home *** CD-ROM | disk | FTP | other *** search
/ CD Actual 1 / PC Actual CD 01.iso / share / dos / graficos / plydoc14.arj / POLYRAY.DOC < prev    next >
Encoding:
Text File  |  1992-04-09  |  125.2 KB  |  3,600 lines

  1.  
  2.                            Polyray v1.4
  3.                            (c) 1991, 1992
  4.                            Alexander R. Enzmann
  5.                            11 April 1992
  6.                            All Rights Reserved
  7.  
  8. Table of contents
  9.  
  10. 1 Introduction
  11. 1.1 Origin and Credits
  12. 1.2 Useful Tools
  13. 1.3 Contents of This Document
  14. 1.4 Command Line Options
  15. 1.5 Initialization File
  16. 1.6 Quick demo
  17. 1.7 Rendering Options
  18. 1.7.1 Raytracing
  19. 1.7.1.1 Antialiasing
  20. 1.7.1.2 Dithering
  21. 1.7.1.3 Bounding Slabs
  22. 1.7.1.4 Global Shading Flags
  23. 1.7.2 Scan Conversion
  24. 2  Detailed Description of the Polyray Input Format
  25. 2.1 Expressions
  26. 2.1.1 Numeric expressions
  27. 2.1.2 Vector Expressions
  28. 2.1.3 Conditional Expressions
  29. 2.1.4 Run-Time expressions
  30. 2.1.5 Named Expressions
  31. 2.2 Definition of the viewpoint
  32. 2.3 Objects/Surfaces
  33. 2.3.1 Object Modifiers
  34. 2.3.1.1 Position and Orientation Modifiers
  35. 2.3.1.1.1 Translate
  36. 2.3.1.1.2 Rotate
  37. 2.3.1.1.3 Scale
  38. 2.3.1.1.4 Shear
  39. 2.3.1.2 Bounding Objects
  40. 2.3.1.3 Clipping Objects
  41. 2.3.1.4 Subdivision of Primitives
  42. 2.3.1.5 Shading Flags
  43. 2.3.2 Primitives
  44. 2.3.2.1 Bezier patch
  45. 2.3.2.2 Blob
  46. 2.3.2.3 Box
  47. 2.3.2.4 Cone
  48. 2.3.2.5 Cylinder
  49. 2.3.2.6 Disc
  50. 2.3.2.7 Implicit function
  51. 2.3.2.8 Height Field
  52. 2.3.2.8.1 File Based Height Fields
  53. 2.3.2.8.1.1 16 Bit Height Files
  54. 2.3.2.8.1.2 24 Bit Height Files
  55. 2.3.2.8.2 Implicit Height Fields
  56. 2.3.2.9 Lathe Surface
  57. 2.3.2.10 Parabola
  58. 2.3.2.11 Polygon
  59. 2.3.2.12 Polynomial Function
  60. 2.3.2.13 Sphere
  61. 2.3.2.14 Sweep Surface
  62. 2.3.2.15 Torus
  63. 2.3.2.16 Triangular patch
  64. 2.3.3 Constructive Solid Geometry (CSG)
  65. 2.3.4 Bounding Slabs
  66. 2.4 Color and Lighting
  67. 2.4.1 Light Sources
  68. 2.4.1.1 Positional Lights
  69. 2.4.1.2 Spot Lights
  70. 2.4.2 Background Color
  71. 2.4.3 Textures
  72. 2.4.3.1 Procedural Textures
  73. 2.4.3.1.1 Standard Shading Model
  74. 2.4.3.1.1.1 Ambient Light
  75. 2.4.3.1.1.2 Diffuse Light
  76. 2.4.3.1.1.3 Specular Highlights
  77. 2.4.3.1.1.4 Reflected Light
  78. 2.4.3.1.1.5 Transmitted Light
  79. 2.4.3.1.1.3 Microfacet Distribution
  80. 2.4.3.1.2 Checker Texture
  81. 2.4.3.1.3 Hexagon Texture
  82. 2.4.3.1.4 Noise Surface
  83. 2.4.3.1.5 Radial Texture
  84. 2.4.3.2 Functional Textures
  85. 2.4.3.2.1 Image maps
  86. 2.4.3.2.2 Three dimensional noise
  87. 2.5 Comments
  88. 2.6 Animation support
  89. 2.7 Conditional processing
  90. 2.8 Include files
  91. 2.9 File flush
  92. 3 File Formats
  93. 3.1 Output files
  94. 4 Algorithms
  95. 4.1 Processing polynomial expressions
  96. 4.1.1 Example equation representation
  97. 4.1.2 Allowed Formula Syntax
  98. 4.1.3 Rules for processing formulas
  99. 4.2 Processing of arbitrary functional surfaces
  100. 4.2.1 Spherical coordinates
  101. 4.3 Three dimensional noise generation
  102. 4.4 Marching Cubes
  103. 5 Outstanding issues
  104. 5.1 To do list
  105. 5.2 Known Bugs
  106. 6 Revision History
  107. 7 Bibliography
  108. 8 Sample files
  109. 8.1 Full sample
  110. 8.2 List of Sample Files
  111. 9 Polyray grammar
  112.  
  113.  
  114. 1 Introduction
  115.  
  116. The program "Polyray" is a raytracer able to render a wide variety of
  117. mathematical shapes.  The means of description range from standard primitives
  118. like box, sphere, etc. to 3 variable polynomial expression, and finally (and
  119. slowest of all) surfaces containing transcendental functions like sin, cos,
  120. log.  The files associated with Polyray are distributed in three pieces:
  121. the executable, a collection of document files, and a collection of data files.
  122.  
  123. This document is written at a fairly detailed level, and as such may not provide
  124. a sufficient introduction to many of the concepts.  If you want a good
  125. introduction to raytracing, buy the book: "Introduction to Ray Tracing",
  126. edited by Andrew Glassner, Academic Press, 1989.  That book is excellent and
  127. will provide many of the background details that are not contained here.
  128.  
  129. Polyray is not the only raytracer that is available through Freeware or
  130. Shareware channels.  Two outstanding raytracers are: POV-Ray (coordinated by
  131. Drew Wells and authored by the Persistence of Vision team) which is Freeware
  132. and available through the raytracing forum on Compuserve (go comart); and
  133. Vivid (written by Stephen Coy) which is Shareware and available from many BBS's.
  134.  
  135. The data files are ASCII text, the image file formats are Targa (see section 3.1
  136. for the supported input and output formats).  It is unlikely that this will
  137. change.  The Targa format is supported by many image processing programs so if
  138. you need to translate between Targa and something else it is quite simple.
  139. (Using the Targa formats also means that I didn't have to define my own format
  140. and then build conversion programs or try to convince others to build
  141. conversion programs.)
  142.  
  143. The display modes include the standard 320x200 VGA color mode, as well as the
  144. "mode13x" display mode for standard VGA boards, and 640x480 256 color modes
  145. for many SVGA boards. SVGA displays are only supported on 286 versions of the
  146. executable (I don't have a 386 to test protected mode access to video).
  147.  
  148. The executable requires IBM PC compatible with at least a 286 and 287 to run.
  149. There are real mode and protected mode versions of the program available - the
  150. protected mode version is recommended if you want to raytrace large data files,
  151. or if you want to use the Z-Buffer for anything but small image sizes.
  152.  
  153. I'm interested in any comments/bug reports.  I can be reached via email by:
  154.  
  155.   Compuserve as Alexander Enzmann 70323,2461
  156.  
  157.   Internet as xander@mitre.org
  158.  
  159. or via the postal service at:
  160.  
  161.       20 Clinton St.
  162.       Woburn, Ma 01801
  163.       USA
  164.  
  165. 1.1 Origin and Credits
  166.  
  167. This original code for this program was based on the "mtv" ray-tracer, written
  168. (and placed in the public domain) by Mark VandeWettering.
  169.  
  170. Many thanks go to David Mason for his numerous comments and suggestions (and
  171. for adding a new feature to DTA every time I needed to test something).  Thanks
  172. also to the Cafe Algiers in Cambridge Ma. for providing a place to get heavily
  173. caffinated and rap about ray-tracing and image processing for hours at a time.
  174.  
  175. 1.2 Useful tools
  176.  
  177. There are several types of tools that you will want to have to work with
  178. this program (in relative order of importance):
  179.  
  180.      o An ASCII text editor for preparing and modifying input files.
  181.  
  182.      o A picture viewer for viewing images.
  183.  
  184.      o An image processing program for translation between Targa and
  185.        some other format.
  186.  
  187.      o An animation generator that will take a series of Targa images and
  188.        produce an animation file.
  189.        
  190.      o An animation viewer for playing an animation on the screen.
  191.  
  192. For the IBM-PC/Clone world (which is what I use at home), there are several
  193. popular and easily available programs:  "Piclab", which will read
  194. process and write several popular graphics file formats,  "VPIC" (Shareware)
  195. which displays images quickly and supports many different video boards, "DTA"
  196. which will take a bunch of Targa files and produce a "FLI" format animation,
  197. and "aaplay" or "play06" which will show a FLI on a VGA screen.
  198.  
  199. 1.3 Contents of this document
  200.  
  201. This document describes the input format and capabilities of the "Polyray"
  202. ray-tracing program.  The following features are supported:
  203.  
  204.    Viewpoint (camera) characteristics,
  205.    Positional (point) and simple directional (spotlight) light sources,
  206.    Background color,
  207.    Surface characteristics of objects,
  208.    Shape primitives:
  209.       Bezier patch, blob, box, cone, cylinder, disc, implicit function,
  210.       height field, lathe surface, parabola, polygon, polynomial function,
  211.       sphere, sweep surface, torus, triangular patches
  212.    Animation support,
  213.    Conditional processing,
  214.    Include files,
  215.    Named values and objects.
  216.    Constructive Solid Geometry (CSG)
  217.    User definable (functional) textures
  218.    Initialization file for default values
  219.  
  220. 1.4 Command Line Options
  221.  
  222. A number of operations can be manipulated through values in an initialization
  223. file, within the data file, or from the command line (processed in that order,
  224. with the last read having the highest precedence).  The command line values
  225. will be displayed if no arguments are given to Polyray.
  226.  
  227. The values that can be specified at the command line, with a brief description
  228. of their meaning are:
  229.  
  230.    -a              Perform simple antialiasing (neighbor averaging)
  231.  
  232.    -A              Perform adaptive antialiasing (based on threshold)
  233.  
  234.    -b pixels       Set the maximum number of pixels that will be calculated
  235.                    between file flushes
  236.  
  237.    -B              Flush the output file every scan line
  238.  
  239.    -d probability  Dither objects using the given probability
  240.  
  241.    -D scale        Dither all rays using the given probability
  242.  
  243.    -J              Perform jittered antialiasing (fixed # of samples/pixel)
  244.  
  245.    -M maxprims     Change the maximum # of primitives (default 1024)
  246.  
  247.    -o filename     The output file name, the default output file name if not
  248.                    specified is "out.tga"
  249.  
  250.    -p bits/pixel   Set the number of bits per pixel in the output file (must
  251.                    be one of 16, 24, 32)
  252.  
  253.    -Q              Abort if any key is hit during trace
  254.  
  255.    -q flags        Turn on/off various global shading options
  256.  
  257.    -R              Resume an interrupted trace.
  258.  
  259.    -s samples      # of samples per pixel when performing antialiasing
  260.  
  261.    -S              Render using scan conversion rather than raytracing
  262.  
  263.    -t status_vals  Status display type [0=none,1=totals,2=line,3=pixel].
  264.  
  265.    -T threshold    Threshold to start oversampling
  266.  
  267.    -u              Write the output file in uncompressed form
  268.  
  269.    -v              Trace from bottom to top
  270.  
  271.    -V mode         Use VGA display while tracing [0=none,1=VGA,2=SVGA]
  272.  
  273.    -W              Wait for key before clearing display
  274.  
  275.    -x columns      Set the x resolution
  276.  
  277.    -y lines        Set the y resolution
  278.  
  279.    -z start_line   Start a trace at a specified line
  280.  
  281. If no arguments are given then Polyray will give a brief description of the
  282. command line options.
  283.  
  284. 1.5 Initialization File
  285.  
  286. The first operation carried out by Polyray is to read the initialization
  287. file "polyray.ini".  This file can be used to tune a number of the default
  288. variables used during rendering.  This file must appear in the current
  289. directory.  This file does not have to exist, it is typically used as a
  290. convenience to eliminate retyping command line parameters.
  291.  
  292. Each entry in the initialization file must appear on a separate line,
  293. and have the form:
  294.  
  295.       default_name     default_value
  296.  
  297. The names are text.  The values are numeric for some names, and text for
  298. others.  The allowed names and values are:
  299.  
  300. abort_test       true/false/on/off
  301. alias_threshold  [Value to cause adaptive anitaliasing to start]
  302. antialias        none/filter/jitter/adaptive
  303. display          none/vga/svga
  304. max_level        [max depth of recursion]
  305. max_lights       [max # of lights]
  306. max_queue_size   [max # of objects in a priority queue]
  307. max_slab_count   [max # of bounding slabs]
  308. max_samples      [# of samples to use with jittered/adaptive antialiasing]
  309. pixel_size       [16, 24, 32]
  310. pixel_encoding   none/rle
  311. renderer         ray_trace/scan_convert
  312. shade_flags      [default/bit mask of flags, see section 1.7.1.4]
  313. shadow_tolerance [miminum distance for blocking objects]
  314. status           none/totals/line/pixel
  315.  
  316. A typical example of "polyray.ini" would be:
  317.  
  318.    abort_test       on
  319.    alias_threshold  0.05
  320.    antialias        adaptive
  321.    display          vga
  322.    max_samples      8
  323.    pixel_size       24
  324.    pixel_encoding   rle
  325.    renderer         ray_trace
  326.    shade_flags      default
  327.    shadow_tolerance 0.05
  328.    status           line
  329.  
  330. If no initialization file exists, then Polyray will use the following
  331. default values:
  332.  
  333.    abort_test       off
  334.    alias_threshold  0.2
  335.    antialias        none
  336.    display          none
  337.    max_level        5
  338.    max_lights       10
  339.    max_queue_size   100
  340.    max_slab_count   6
  341.    max_samples      4
  342.    pixel_size       16
  343.    pixel_encoding   rle
  344.    renderer         ray_trace
  345.    shade_flags      default
  346.    shadow_tolerance 0.001
  347.    status           none
  348.    
  349.  
  350. 1.6 Quick demo
  351.  
  352. For a (sort of) quick demo of running polyray, simply enter (at the command
  353. line):
  354.  
  355.       polyray sphere.pi -o sphere.tga -V 1
  356. or
  357.       polyray cossph.pi -o cossph.tga -V 1
  358.  
  359. If you do not have a VGA board, then instead of the -V option, use -t.  Instead
  360. of an on-screen display you will see the line that Polyray is currently
  361. rendering.  When it finishes, use an image viewer to see what it did.  If you
  362. have Piclab, then enter the commands:
  363.  
  364.    C> piclab
  365.    > tload sphere             (or "tload cossph" if you rendered that data file)
  366.    > makepal
  367.    > map
  368.    > show
  369.  
  370. That series of commands will load the image, pick an approproate pallette, map
  371. the colors in the image to the pallette, then display the image on-screen.  You
  372. should see a greatly improved image quality over the display that is shown
  373. during tracing.
  374.  
  375. 1.7 Rendering Options
  376.  
  377. Polyray supports two very distinct means of rendering scenes: raytracing
  378. and polygon scan conversion.  Raytracing is often a very time consuming
  379. process, however a number of types of surfaces can be rendered with this
  380. technique that are very difficult or impossible using traditional techniques.
  381. All of the primitives that are described in this document can be rendered
  382. with either raytracing or scan conversion.
  383.  
  384. If a bound is given for an implicit function or polynomial functions, then
  385. a marching cubes algorithm is used to generate polygons that approximate the
  386. surface.  If a bound is not given, then the scan conversion process will not
  387. work.
  388.  
  389. 1.7.1 Raytracing
  390.  
  391. Polyray is at heart a raytracer.  The quality of the images that can be produced
  392. is entirely a function of how long you want to wait for results.  There are
  393. certain options that allow you to adjust how you want to trade off quality vs.
  394. speed vs memory requirements.
  395.  
  396. The basic operation in raytracing is that of shooting a ray from the eye,
  397. through a pixel, and finally hitting an object.  For each type of primitive
  398. there is specialized code that helps determine if a ray has hit that primitive.
  399. The standard way that Polyray generates an image is to use one ray per pixel
  400. and to test that ray against all of the objects in the data file.
  401.  
  402. The following sections describe how you can cause Polyray to use more rays per
  403. pixel to improve image quality, skip pixels or objects in a probabilistic way
  404. to improve rendering speed, or partition objects in such a way that not all
  405. objects need to be tested for every ray.  Each of these techniques has benefits
  406. and drawbacks.
  407.  
  408. 1.7.1.1 Antialiasing
  409.  
  410. The representation of rays is as a 1 dimensional line.  On the other hand pixels
  411. and objects have a definite size.  This can lead to a problem known as
  412. "aliasing", where a ray may not intersect an object because the object only
  413. partially overlaps a pixel, or the pixel should have color contributed by
  414. several objects that overlap it, none of which completely fills the pixel.
  415. Aliasing often shows up as a staircase effect on the edges of objects.
  416.  
  417. Polyray offers two ways to reduce aliasing: by filtering, and by oversampling.
  418. Filtering smooths the output image by averaging the color values of neighboring
  419. pixels to the pixel being rendered.  Oversampling is performed by adding extra
  420. rays through random jittering of the direction of the ray within the pixel being
  421. traced.  By averaging the result of all of the rays that are shot through a
  422. single pixel, aliasing problems can be greatly reduced.
  423.  
  424. The filtering process adds little overhead to the rendering process, however the
  425. resolution of the image is degraded by the averaging process.  Jittered
  426. antialiasing slows down the rendering process in direct proportion to the
  427. number of extra rays, but results in the best image quality.
  428.  
  429. Oversampling can be performed in two ways, either by using a fixed number of
  430. rays per pixel, or by adaptive antialiasing.  The former will always shoot the
  431. same number of rays through each pixel, regardless of picture complexity.  The
  432. latter initially shoots just one ray through each pixel, if a pixel's color is
  433. significantly different that any of its neighbors, then additional rays are fired.
  434.  
  435. The two initialization (and command line) variables that will affect the
  436. performance of adaptive antialiasing are "alias_threshold" and "max_samples".
  437. The first is a measure of how different a pixel must be with respect to its
  438. neighbors before antialiasing will kick in.  If a pixel has the value:
  439. <r1, g1, b1>, and it's neighbor has the value <r2, g2, b2> (RGB values between
  440. 0 and 1 inclusive), then the "distance" between the two colors is:
  441.  
  442.    dist = sqrt((r1 - r2)^2 + (b1 - b2)^2 + (g1 - g2)^2)
  443.  
  444. This is the standard pythagorean formula for values specified in RGB.  If "dist"
  445. is greater than the value of "alias_threshold", then extra rays will be fired
  446. through the pixel in order to determine an averaged color for that pixel.
  447.  
  448.  
  449. Note:  Performing the distance test in RGB space may not be the best way
  450. to determine when antialiasing should occur.  Future versions of Polyray
  451. may perform distance calculations in LAB space.
  452.  
  453. 1.7.1.2 Dithering
  454.  
  455. In order to speed up the generation of an image (and to produce some interesting
  456. effects), several dithering options are available: Dithering all rays, dithering
  457. all objects, and dithering of specific objects.  Associated with each option is
  458. a probability value between 0 and 1.  During rendering, if the dithering option
  459. is being used, Polyray generates a random number between 0 and 1 and compares it
  460. to the probability value.  If the random number is greater than the probability
  461. value then the ray (or object) will be ignored.
  462.  
  463. Dithering of rays is a way to sample the entire image, for example if a
  464. probability value of 0.5 is given, then only half of all rays will be traced
  465. through the scene.  The final image will be severly degraded, however the
  466. amount of time taken to trace the scene will be cut approximately in half.
  467.  
  468. Dithering of objects is a way to simulate transparency, without the overhead of
  469. generating secondary rays during the raytracing process.  It also can be used
  470. as an interesting optical effect - during an animation, if the probability value
  471. is successively lowered from 1 to 0, the object will dissolve away.
  472.  
  473. Negative dither values as well as those above 1.0 will have no effect.  The
  474. way dithering works is:  Right before a check is made to see if the current
  475. ray will intersect an object a random number between 0 and 1 is generated.  If
  476. this number is less than the dither value then the intersection check will
  477. be made.  If the random number is greater than the dither value then Polyray
  478. assumes that there is no hit.
  479.  
  480. Sample files:  dither.pi, bnddithr.pi
  481.  
  482. 1.7.1.3 Bounding Slabs
  483.  
  484. For scenes with large numbers of small objects, there are optimization tricks
  485. that can take advantage of the distribution of the objects.  An easy one to
  486. implement, and one that often results in huge time savings are bounding slabs.
  487. The basic idea of a bounding slab is to sort all objects along a particular
  488. direction.  Once this sorting step has been performed, then during rendering
  489. the ray can be quickely checked against a slab (which can represent many
  490. objects rather than just one) to see if intersection tests need to be made on
  491. the contents of the slab.
  492.  
  493. The most important caveats with Polyray's implementation of bounding slabs are:
  494.  
  495.    o Scenes with only a few large objects will derive little speed benefits.
  496.  
  497.    o Complex objects defined with CSG will cause problems in the sorting
  498.      process.
  499.    
  500.    o If there is a lot of overlap of the positions of the objects in the scene,
  501.      then there will be little advantage to the slabs.
  502.    
  503.    o If the direction of the slabs does not correspond to a direction that
  504.      easily sorts objects, then there will be little speed gained.
  505.  
  506. However, for data files that are generated by another program, the requirements
  507. for effective use of bounding slabs are often met.  For example, most of the
  508. data files generated by the SPD programs will be rendered orders of magnitude
  509. faster with bounding slabs than without.
  510.  
  511. 1.7.1.4 Shading Quality Flags
  512.  
  513. By secifying a series of bits, various shading options can be turned on and
  514. off.  The value of each flag, as well as the meaning are:
  515.  
  516.    1      Shadow_Check      Shadows will be generated
  517.    2      Reflect_Check     Reflectivity will be tested
  518.    4      Transmit_Check    Check for refraction
  519.    8      Two_Sides         If on, highlighting will be performed on both
  520.                             sides of a surface.
  521.   16      Cast_Shadow       Determines if an object can cast a shadow
  522.  
  523. The default settings of these flags are:
  524.  
  525.    raytracing     : Shadow_Check + Reflect_Check + Transmit_Check +
  526.                     Two_Sides + Cast_Shadow (which = 31)
  527.    scan conversion: [none, which = 0]
  528.  
  529. The assumption made is that during raytracing the highest quality is desired,
  530. and consequently every shading test is made.  The assumption for scan
  531. conversion is that you are trying to render quickly, and hence most of the
  532. complex shading options are turned  off.
  533.  
  534. If any of the flags are explictly set and scan conversion is used to render
  535. the scene, then at every pixel that is displayed, a recursive call to the
  536. raytracer will be made to determine the correct shading.  Note that due to
  537. the faceted nature of objects during scan conversion, shadowing, and
  538. especially refraction can get messed up during scan conversion.
  539.  
  540. For example if you want to do a scan conversion that contains shadows,
  541. you would use the following:
  542.  
  543.    polyray xxx.pi -S -q 1
  544.  
  545. or if you wanted to do raytracing with no shadows, reflection turned on,
  546. transparency turned off, and with diffuse and specular shading performed
  547. for both sides of surfaces you would use options 2 and 8:
  548.  
  549.    polyray xxx.pi -q 10
  550.  
  551. Note: texturing cannot be turned off.
  552.  
  553. 1.7.2 Scan Conversion
  554.  
  555. In order to support a quicker render of images Polyray can render most
  556. primitives as a series of polygons.  Each polygon is scan converted using a
  557. Z-Buffer for depth information, and a S-Buffer for color information.
  558.  
  559. The scan conversion process does not by default provide support for: shadows,
  560. reflectivity, or transparency.  It is possible to instruct Polyray to use
  561. raytracing to perform these shading operations through the use of either
  562. the global shade flags or by setting shade flags for a specific object.
  563. An alternative method for quickly testing shadows using shadow buffers is in
  564. the works.
  565.  
  566. The memory requirements for performing scan conversion can be quite substantial.
  567. You need at least as much memory as is required for raytracing, plus at least
  568. 7 bytes per pixel for the final image.  In order to correctly keep track of
  569. depth and color - 4 bytes are used for each pixel in the Z-Buffer (32 bit
  570. floating point number), and 3 bytes are used for each pixel in the S-Buffer
  571. (1 byte each for red, green, and blue).
  572.  
  573. During scan conversion, the number of polygons used to cover the surface of
  574. a primitive is controlled using the keywords "u_steps", and "v_steps".  These
  575. two values control how many steps around and along the surface of the object
  576. values are generated to create polygons.  The higher the number of steps, the
  577. smoother the final appearance.  Note however that if the object is very small
  578. then there is little reason to use a fine mesh - hand tuning is sometimes
  579. required to get the best balance between speed and appearance.
  580.  
  581. Generating isosurfaces for blobs, polynomial functions and implicit functions,
  582. followed by polygonalization of the surfaces is performed using a "marching
  583. cubes" algorithm.  Currently the value of "u_steps" determines the number of
  584. slices along the x-axis, and the value of "v_steps" controls the number of
  585. slices along the y-axis and along the z-axis.  Future versions may introduce
  586. a third value to allow independant control of y and z.
  587.  
  588. 2  Detailed description of the Polyray input format:
  589.  
  590. An input file describes the basic components of an image:
  591.  
  592.    o A viewpoint that characterises where the eye is, where it is looking
  593.      and what its orientation is.
  594.      
  595.    o Objects, their shape, placement, and orientation.
  596.    
  597.    o Light sources, their placement and color.
  598.  
  599. Beyond the fundamentals, there are many components that exist either as
  600. a convienience such as definable expressions, or textures.  This section
  601. of the document describes in detail the syntax of all of the components
  602. of an input file
  603.  
  604. 2.1 Expressions
  605.  
  606. There are three basic types of expressions that are used in polyray:
  607.  
  608.    o fexper        - Floating point expression (i.e. 0.5, 2 * sin(1.33))
  609.                      These are used at any point a floating point value
  610.                      is needed, such as the radius of a sphere or the
  611.                      amount of contribution of a part of the lighting model.
  612.  
  613.    o vexper        - Vector valued expression  (i.e. <0, 1, 0>, red,
  614.                      12 * <2, sin(x), 17> + P).  Used for color expressions,
  615.                      describing positions, describing orientations, etc.
  616.  
  617.    o cexper        - Conditional expression (i.e. x < 42).
  618.  
  619. The following sections describe the syntax for each of these types of
  620. expressions, as well as how to define variables in terms of expressions.
  621.  
  622. 2.1.1 Numeric expressions
  623.  
  624. In most places where a number can be used (i.e. scale values, angles, RGB
  625. components, etc.) a simple floating point expression (fexper) may be used.
  626. These expressions can contain any of the following terms:
  627.  
  628.    val                  - A floating point number or defined value
  629.    '(' fexper ')'       - Parenthesised expression
  630.    fexper ^ fexper      - Same as pow(x, y)
  631.    fexper * fexper      - Multiplication
  632.    fexper / fexper      - Division
  633.    fexper + fexper      - Addition
  634.    fexper - fexper      - Subtraction
  635.    -fexper              - Unary minus
  636.    acos(fexper)         - Arccosine, (input in radians for all trig functions)
  637.    asin(fexper)         - Arcsin
  638.    atan(fexper)         - Arctangent
  639.    ceil(fexper)         - Ceiling function
  640.    cos(fexper)          - Cosine
  641.    cosh(fexper)         - Hyperbolic cosine
  642.    degrees(fexper)      - Converts radians to degrees
  643.    exp(fexper)          - e^x, standard exponential function
  644.    fabs(fexper)         - Absolute value
  645.    floor(fexper)        - Floor function
  646.    fmod(fexper,fexper)  - Modulus function for floating point values
  647.    ln(fexper)           - Natural logarithm
  648.    log(fexper)          - Logarithm base 10
  649.    noise(vexper,fexper) - Correlated noise function (useful for solid texturing)
  650.    pow(fexper,fexper)   - Exponentiation (x^y)
  651.    radians(fexper)      - Converts degrees to radians
  652.    sin(fexper)          - Sine
  653.    sinh(fexper)         - Hyperbolic sine
  654.    sqrt(fexper)         - Square root
  655.    tan(fexper)          - Tangent
  656.    tanh(fexper)         - Hyperbolic tangent
  657.    visible(vexper,      - Returns 1 if the second point visible from the first.
  658.            vexper)
  659.    vexper[i]            - Extract component i from a vector (0 <= i <= 2)
  660.    vexper . vexper      - Dot product of two vectors
  661.    |fexper|             - Absolute value (same as fabs)
  662.    |vexper|             - Length of a vector
  663.  
  664. 2.1.2 Vector Expressions
  665.  
  666. In most places where a vector can be used (i.e. color values, rotation angles,
  667. locations, ...), a vector expression is allowed.  The expressions can contain
  668. any of the following terms: 
  669.  
  670.  
  671.    vexper + vexper        - Addition
  672.    vexper - vexper        - Subtraction
  673.    vexper * vexper        - Cross product
  674.    vexper * fexper        - Scaling of a vector by a scalar
  675.    fexper * vexper        - Scaling of a vector by a scalar
  676.    vexper / fexper        - Inverse scaling of a vector by a scalar
  677.    brownian(vexper)       - Makes a random displacement of a vector
  678.    color_wheel(x, y, z)   - RGB color wheel using x and z (y ignored), the
  679.                             color returned is based on <x, z> using the
  680.                             chart below:
  681.  
  682.                                     Z-Axis
  683.                                        ^
  684.                                        |
  685.                                        |
  686.                                  Green   Yellow
  687.                                      \   /
  688.                                       \ /
  689.                              Cyan ---- * ---- Red  -----> X-Axis
  690.                                       / \
  691.                                      /   \
  692.                                   Blue   Magenta
  693.  
  694.                           Intermediate colors are generated by interpolation.
  695.  
  696.    rotate(vexper, vexper) - Rotate the point specified in the first argument
  697.                             in the first argument by the angles specified in
  698.                             the second argument (angles in degrees).
  699.  
  700. 2.1.3 Conditional Expressions
  701.  
  702. Conditional expressions are used in one of two places: conditional processing
  703. of declarations (see section 2.7) or conditional value functions.
  704.  
  705. cexper has one of the following forms:
  706.  
  707.       !cexper
  708.       cexper && cexper
  709.       cexper || cexper
  710.       fexper < fexper
  711.       fexper <= fexper
  712.       fexper > fexper
  713.       fexper >= fexper
  714.  
  715. A use of conditional expressions is to define a texture based on other
  716. expressions, the format of this expression is:
  717.  
  718.    (cexper ? true_value : false_value)
  719.  
  720. Where true_value/false_value can be either floating point or vector values.
  721. This type of expression is taken directly from the equivalent in the C
  722. language.  An example of how this is used (from the file "spot1.pi") is:
  723.  
  724.    special surface {
  725.       color white
  726.       ambient (visible(W, throw_offset) == 0
  727.                ? 0
  728.                : (P[0] < 1 ? 1
  729.                  : (P[0] > throw_length ? 0
  730.                     : (throw_length - P[0]) / throw_length)))
  731.       transmission (visible(W, throw_offset) == 1
  732.                     ? (P[0] < 1 ? 0
  733.                        : (P[0] > throw_length ? 1
  734.                           : P[0] / throw_length))
  735.                     : 1), 1
  736.       }
  737.  
  738. In this case conditional statements are used to determine the surface
  739. characteristics of a cone defining the boundary of a spotlight.  The amount
  740. of ambient light is modified with distance from the apex of the cone, the
  741. visibility of the cone is modified based on both distance and on a determination
  742. if the cone is behind an object with respect to the source of the light.
  743.  
  744. 2.1.4 Run-Time expressions
  745.  
  746. There are a few expressions that only have meaning during the rendering process:
  747.  
  748.    I                    - The direction of the ray that struck the object
  749.    P                    - The point of intersection in "object" coordinates
  750.    L                    - The index of the light source currently being checked
  751.                           (used during diffuse and specular calculations only).
  752.    N                    - The normal to the point of intersection in "world"
  753.                           coordinates
  754.    W                    - The point of intersection in "world" coordinates
  755.  
  756. These expressions describe the interaction of a ray and an object.  To
  757. use them effectively, you need to understand the distinction between "world"
  758. coordinates and "object" coordinates.  Object coordinates describe a point or
  759. a direction with respect to an object as it was originally defined.  World
  760. coordinates describe a point with respect to an object after it has been
  761. rotated/translated/scaled.  Typically texturing is done in object coordinates
  762. so that as the object is moved around the texture will move with it.  On the
  763. other hand shading is done in world coordinates.
  764.  
  765. 2.1.5 Named Expressions
  766.  
  767. A major convience for creating input files is the ability to create named
  768. definitions of surface models, object definitions, vectors, etc.  The way
  769. a value is defined takes one of the following forms:
  770.  
  771.    define token expression               - Can be: fexper, vexper, cexper
  772.    define token "str..."
  773.    define token object { ... }
  774.    define token surface { ... }
  775.    define token texture { ... }
  776.  
  777. Objects, surfaces, and textures can either be instantiated as-is by using the
  778. token name alone, or it can be instantiated and modified:
  779.  
  780.    token,
  781. or
  782.    token { ... modifiers ... },
  783.  
  784. Polyray keeps track of what type of entity the token represents and will parse
  785. the expressions accordingly.
  786.  
  787. Note:
  788.    It is not possible to have two types of entities refered to by the same name.
  789.    
  790.    If a name is reused, then a warning will be printed, and all references to
  791.    that name will use the new definition from that point on.
  792.  
  793. 2.2 Definition of the viewpoint
  794.  
  795. The viewpoint and its associated components define the position and orientation
  796. the view will be generated from.
  797.  
  798. The format of the declaration is:
  799.  
  800.     viewpoint {
  801.        from vexper
  802.        at vexper
  803.        up vexper
  804.        angle fexper
  805.        hither fexper
  806.        resolution fexper, fexper
  807.        aspect fexper
  808.        yon fexper
  809.        dither_rays fexper
  810.        dither_objects fexper
  811.        max_trace_depth fexper
  812.        }
  813.  
  814. Order of the entries defining the viewpoint is not important, unless you
  815. redefine some field. (In which case the last is used.)
  816.  
  817. The parameters are:
  818.  
  819.     aspect         : The ratio of width to height. (Default: 1.0.)
  820.     at             : A position to be at the center of the image, in XYZ world
  821.                      coordinates. (Default: <0, 0, 0>)
  822.     angle          : The field of view (in degrees), from the center of the top
  823.                      row to the center of the bottom row. (Default: 45 degrees)
  824.     from           : The eye location in XYZ. (Default: <0, 0, -1>)
  825.     hither         : Distance to front of view pyramid.  Any intersection less
  826.                      than this value will be ignored.  (Defaults to 1.0e-3)
  827.     resolution     : The number of pixels wide and high of the raster.
  828.                      (Default: 256x256)
  829.     up             : A vector defining which direction is up, as an XYZ vector.
  830.                      (Default: <0, 1, 0>)
  831.     yon            : Distance to back of view pyramid.  Any intersection beyond
  832.                      this distance will be ignored. (Defaults to 1.0e5)
  833.     dither_rays    : Rays will be skipped if a random number is above the given
  834.                      value.
  835.     dither_objects : For each ray, Ray-surface checks will skipped for an object
  836.                      if a random number is above the given value.
  837.     max_trace_depth: This allows you to tailor the amount of recursion allowed
  838.                      for scenes with reflection and/or transparency.
  839.                      (Default: 5)
  840.  
  841. The view vectors will be coerced so that they are perpendicular to the vector
  842. from the eye (from) to the point of interest (at).
  843.  
  844. A typical declaration is:
  845.  
  846.    viewpoint {
  847.       from <0, 5, -5>
  848.       at   <0, 0,  0>
  849.       up   <0, 1,  0>
  850.       angle 30
  851.       resolution 320, 160
  852.       aspect 2
  853.       }
  854.  
  855. In this declaration the eye is five units behind the origin, five units above
  856. the x-z plane and is looking at the origin.  The up direction is aligned with
  857. the y-axis, the field of view is 30 degrees and the output file will default to
  858. 320x160 pixels.
  859.  
  860. In this example it is assumed that pixels are square, and hence the aspect
  861. ratio is set to x_resolution/y_resolution.  If you were generating an image
  862. for a screen that has pixels half as wide as they are high then the aspect
  863. ratio would be set to one.
  864.  
  865. 2.3 Objects/Surfaces
  866.  
  867. In order to make pictures, the light has to hit something.  Polyray supports
  868. several primitive objects, and the following sections describe the syntax for
  869. describing the primitives, as well as how more complex primitives can be
  870. built from simple ones.
  871.  
  872. The "object" declaration is how polyray associates a surface with its lighting
  873. characteristics, its bounding shapes, and its clipping shapes.  This declaration
  874. includes one of the primitive shapes (sphere, polygon, ...), an optional
  875. texture declaration (familiar as the TEXTURE declaration in POV-Ray, and set
  876. to a matte white if none is defined), and optionally a bounding shape and/or a
  877. clipping shape.
  878.  
  879. The format the declaration is:
  880.  
  881.    object {
  882.       shape_declaration
  883.       [texture_declaration]
  884.       [translate/rotate/scale declarations]
  885.       [subdivision declarations]
  886.       [bounds declaration]
  887.       [clips declaration]
  888.       }
  889.  
  890. There are two separate ways that an object can be rendered by Polyray,
  891. raytracing or scan conversion.  The steps taken by each of these methods are:
  892.  
  893. Raytracing
  894.  
  895.    1) Test the ray against the bounding object.  If it doesn't hit then
  896.       don't bother looking for intersections with the object itself.
  897.  
  898.    2) Find all intersections of the ray with the object.  (Up to the
  899.       maximum number of intersections.)
  900.  
  901.    3) Find the closest point of intersection that is "inside" the
  902.       clipping object.
  903.  
  904. Scan Conversion
  905.  
  906.    1) The object is broken up into a number of rectangles (the actual number
  907.       depends on the values of "u_steps" and "v_steps" in the object
  908.       declarations).
  909.  
  910.    2) The rectangle is clipped so that only the visible part will be rendered.
  911.  
  912.    3) The clipped polygon is scan converted a line at a time.  As the scan
  913.       conversion takes place, the object and world coordinates of the polygon
  914.       are interpolated from vertices.
  915.  
  916.    4) As each pixel is generated by scan conversion, its distance from the eye
  917.       is checked against a Z-Buffer.
  918.       
  919.    5) If the distance is less than the value in the Z-Buffer, then any CSG and
  920.       clipping operations associated with the object are performed.
  921.       
  922.    6) If the pixel passes the depth check and CSG checks, then the pixel is
  923.       shaded using the texture information associated with the object.  The
  924.       depth to the pixel is stored in the Z-Buffer and the color associated
  925.       with the pixel is stored in the S-Buffer.
  926.  
  927. Determining if a point is inside an object is performed by evaluating the
  928. function that describes the object using the point of intersection.  If
  929. the value is less than or equal to 0 then the point is inside.  Some
  930. primitives do not have an inside (triangular patches), others do not have
  931. a well defined inside (cylinder).
  932.  
  933. The following sub-sections describe the format of the individual parts of an
  934. an object declaration.  (Note:  The surface declaration MUST be first in the
  935. declaration, as any operations that follow have to have data to work on.)
  936.  
  937. 2.3.1 Object Modifiers
  938.  
  939. 2.3.1.1 Position and Orientation Modifiers
  940.  
  941. The position, orientation, and size of an object can be modified through one of
  942. four linear transformations: translation, rotation, scaling, and shear.
  943.  
  944. 2.3.1.1.1 Translation
  945.  
  946. Translation moves the position of an object by the number of units specified
  947. in the associated vector.  The format of the declaration is:
  948.  
  949.    translate <xt, yt, zt>
  950.  
  951.  
  952. 2.3.1.1.2 Rotation
  953.  
  954. Rotation revolves the position of an object about the x, y, and z axes (in that
  955. order).  The amount of rotation is specified in degrees for each of the axes.
  956. The direction of rotations follows a left-handed convention: if the thumb of
  957. your left hand points along the positive direction of an axis, then the
  958. direction your fingers curl is the positive direction of rotation.
  959.  
  960. The format of the declaration is:
  961.  
  962.    rotate <xr, yr, zr>
  963.    
  964. For example the declaration:
  965.  
  966.    rotate <30, 0, 20>
  967.  
  968. will rotate the object by 30 degrees about the x axis, followed by 20 degrees
  969. about the z axis.
  970.  
  971. Remember: Left Handed Rotations.
  972.  
  973. 2.3.1.1.3 Scaling
  974.  
  975. Scaling alters the size of an object by a given amount with respect to each of
  976. the coordinate axes.  The format of the declaration is:
  977.  
  978.    scale <xs, ys, zs>
  979.  
  980. 2.3.1.1.4 Shear
  981.  
  982. A less frequently used, but occasionally useful transformation is linear shear.
  983. Shear scales along one axis by an amount that is proportional to the location
  984. on another axis.  The format of the declaration is:
  985.  
  986.    shear yx, zx, xy, zy, xz, yz
  987.  
  988. Typically only one or two of the components will be non-zero, for example the
  989. declaration:
  990.  
  991.    shear 0, 0, 1, 0, 0, 0
  992.  
  993. will shear an object more and more to the right as y gets larger and larger.
  994. The order of the letters in the declaration is descriptive, shear ... ab, ...
  995. means shear along direction a by the amount "ab" times the position b.
  996.  
  997. This declaration should probably be split into three: one that associates shear
  998. in x with the y and z values, one that associates shear in y with x and z
  999. values, and one that associates shear in z with x and y values.
  1000.  
  1001. You might want to look at the file "xander.pi" - this uses shear on boxes to
  1002. make diagonally slanted parts of letters.
  1003.  
  1004. 2.3.1.2 Bounding objects
  1005.  
  1006. In order to speed up the process of determining if a ray intersects an object,
  1007. a bounding shape can be specified.  The purpose for a bounding object is to
  1008. give the raytracer a better idea of where the object is.  If the ray does
  1009. not intersect the bounding object, then the raytracer will not attempt to
  1010. find intersections with the object itself.  For very complex CSG objects, using
  1011. a sphere or other simple bounding shape can greatly improve performance.
  1012.  
  1013. The bounding shape is also used during the process of generating bounding slabs,
  1014. and during the scan conversion of polynomial and implicit functions.
  1015.  
  1016. An example of the use of a bounding shape for a polynomial surface (a Torus
  1017. in this case):
  1018.  
  1019.    define torus_expression (x^2 + y^2 + z^2 - (r0^2 + r1^2))^2 -
  1020.                            4 * r0^2 * (r1^2 - z^2)
  1021.    object {
  1022.       polynomial torus_expression
  1023.       root_solver Ferrari
  1024.       shiny_red
  1025.       bounds object { box <-(r0+r1), -(r0+r1), -r1>,
  1026.                           < (r0+r1),  (r0+r1),  r1> }
  1027.       }
  1028.  
  1029. The test for intersecting a ray against a box is much faster that performing
  1030. the test for the polynomial equation.  In addition the box helps the scan
  1031. conversion process determine where to look for the surface of the torus.
  1032.  
  1033. 2.3.1.3 Clipping objects
  1034.  
  1035. Clipping object are a way of selectively removing parts of a surface.  The
  1036. way they work is very similar to an intersection with another object that
  1037. is completely transparent.  This operation can be very useful when displaying
  1038. complex polynomial functions, these functions can have sheets zooming off
  1039. to infinity that would otherwise obscure the portion of the surface you are
  1040. interested in.
  1041.  
  1042. When a ray-object intersection is found, the point of intersection is tested
  1043. to see if it is inside the clipping object.  If it is not inside, then that
  1044. point is thrown away.
  1045.  
  1046. An example of how this can be used is (from the data file "devil.pi"):
  1047.  
  1048.    object {
  1049.       polynomial x^4 + 2*x^2*z^2 - 0.36*x^2 - y^4 + 0.25*y^2 + z^4
  1050.       root_solver Ferrari
  1051.       bounds object { sphere <0, 0, 0>, 3 }
  1052.       clips  object { box <-2, -2, -0.5>, <2, 2, 0.5> }
  1053.       rotate <40, 30, 0>
  1054.       shiny_red
  1055.       }
  1056.  
  1057. This surface will be trimmed so that only the points within the box will
  1058. be retained.
  1059.  
  1060. 2.3.1.4 Subdivision of Primitives
  1061.  
  1062. The amount of subdivision of a primitive that is performed before it is
  1063. displayed as polygons is tunable.  These declarations only take effect during
  1064. scan conversion - they are ignored during raytracing.  The two declarations are:
  1065.  
  1066.    u_steps n
  1067.    v_steps m
  1068.  
  1069. Where U generally refers to the number of steps "around" the primitive (the
  1070. number of steps around the equator of a sphere for example).  The parameter V
  1071. refers to the number of steps along the primitive (latitudes on a sphere).
  1072. Cone and cylinder primitives only require 1 step along V, but for smoothness
  1073. may require many steps in U.
  1074.  
  1075. For blobs, the v_steps component plays double duty, specifying how many
  1076. subdivisions to perform along both the y-axis and the z-axis.
  1077.  
  1078. 2.3.1.5 Shading Flags
  1079.  
  1080. It is possible to tune the shading that will be performed for each object.
  1081. The values of each bit in the flag has the same meaning as that given for
  1082. global shading in section 1.7.1.4:
  1083.  
  1084.    1      Shadow_Check      Shadows will be generated
  1085.    2      Reflect_Check     Reflectivity will be tested
  1086.    4      Transmit_Check    Check for refraction
  1087.    8      Two_Sides         If on, highlighting will be performed on both
  1088.                             sides of a surface.
  1089.   16      Cast_Shadow       Determines if an object can cast a shadow
  1090.  
  1091. The declaration has the form:
  1092.  
  1093.    shading_flags xx
  1094.  
  1095. i.e. if the value 18 is used for "xx" above, then this object can be reflective
  1096. and will cast shadows, however there will be no tests for transparency and
  1097. there will be no shading of the back sides of surfaces.
  1098.  
  1099. Note: the shading flag only affects the object in which the declaration is
  1100. made.  This means that if you want the shading values affected for all parts
  1101. of a CSG object, then you will need a declaration in every component.
  1102.  
  1103. 2.3.2 Primitives
  1104.  
  1105. Primitives are the lowest level of shape description.  Typically a scene will
  1106. contain many primitives, appearing either individually or as aggregates using
  1107. Constructive Solid Geometry (CSG) operations.
  1108.  
  1109. The primitive shapes that can be used in Polyray include the following:
  1110.  
  1111.    o Bezier patch
  1112.    o Blob
  1113.    o Box
  1114.    o Cone
  1115.    o Cylinder
  1116.    o Disc
  1117.    o Implicit surface
  1118.    o Height field
  1119.    o Lathe surface
  1120.    o Parabola
  1121.    o Polygon
  1122.    o Polynomial surface
  1123.    o Sphere
  1124.    o Sweep surface
  1125.    o Torus
  1126.    o Triangular patch
  1127.  
  1128. Descriptions of each of these primitive shapes, as well as references to data
  1129. files that demonstrate them are given in the following subsections.  Following
  1130. the description of the primitives.
  1131.  
  1132. 2.3.2.1 Bezier patches
  1133.  
  1134. A Bezier patch is a form of bicubic patch that interpolates its control
  1135. vertices.  The patch is defined in terms of a 4x4 array of control vertices,
  1136. as well as several tuning values.
  1137.  
  1138. The format of the declaration is:
  1139.  
  1140.    bezier subdivision_type, flatness_value,
  1141.           u_subdivisions, v_subdivision,
  1142.           [ 16 comma-separated vertices, i.e.
  1143.              <x0, y0, z0>, <x1, y1, z1>, ..., <x15, y15, z15> ]
  1144.  
  1145. The subdivision type controls how the patch is represented internally.  The
  1146. valid values and their meaning are:
  1147.  
  1148.    1   - Store only the minimum information needed.  Least storage requirement
  1149.          but takes more time during rendering.
  1150.  
  1151.    2   - Store a heirarchical tree of bounding spheres that contain smaller and
  1152.          smaller pieces of the patch.  This tree is used during rendering to
  1153.          speed up the ray-surface intersection process.  Faster but requires
  1154.          more memory.
  1155.          
  1156. The flatness value is used to determine how far a patch should be subdivided
  1157. before it can be considered "flat".  The smaller this value, the more the
  1158. patch will be subdivided (limited by the next two values).
  1159.  
  1160. The number of levels of subdivision of the patch, in each direction, is
  1161. controlled by the two parameters "u_subdivisions", and "v_subdivisions".  The
  1162. more subdivisions allowed, the smoother the approximation to the patch,
  1163. however storage and processing time go up.
  1164.  
  1165. An example of a bezier patch is:
  1166.  
  1167.    object {
  1168.       bezier 2, 0.05, 3, 3,
  1169.          <0, 0, 2>, <1, 0, 0>, <2, 0, 0>, <3, 0,-2>,
  1170.          <0, 1, 0>, <1, 1, 0>, <2, 1, 0>, <3, 1, 0>,
  1171.          <0, 2, 0>, <1, 2, 0>, <2, 2, 0>, <3, 2, 0>,
  1172.          <0, 3, 2>, <1, 3, 0>, <2, 3, 0>, <3, 3,-2>
  1173.    rotate <30, -70, 0>
  1174.    shiny_red
  1175.    }
  1176.  
  1177. Sample files: bezier0.pi, teapot.pi, teapot.inc
  1178.  
  1179. 2.3.2.2 Blob
  1180.  
  1181. A blob describes a smooth potential field around one or more spherical or
  1182. cylindrical components.
  1183.  
  1184. The format of the declaration is:
  1185.  
  1186.    blob threshold:
  1187.       blob_component1
  1188.       [, blob_component2 ]
  1189.       [, etc. for each component ]
  1190.  
  1191. The threshold is the minimum potential value that will be considered when
  1192. examining the interaction of the various components of the blob. Each blob
  1193. component one of two forms:
  1194.  
  1195.    sphere <x, y, z>, strength, radius
  1196. or
  1197.    cylinder <x0, y0, z0>, <x1, y1, z1>, strength, radius
  1198.  
  1199. The strength component describes how strong the potential field is around
  1200. the center of the component, the "radius" component describes the maximum
  1201. distance at which the component will interact with other components.  For a
  1202. spherical blob component the vector <x,y,z> gives the center of the potential
  1203. field around the component.  For a cylindrical blob component the vector
  1204. <x0, y0, z0> defines one end of the axis of a cylinder, the vector <x1, y1, z1>
  1205. defines the other end of the axis of a cylinder.
  1206.  
  1207. Note: The ends of a cylindrical blob component are given hemispherical caps.
  1208.  
  1209. Note: The colon and the commas in the declaration really are important.
  1210.  
  1211.  
  1212. An example of a blob is:
  1213.  
  1214. object {
  1215.       blob 0.5:
  1216.          cylinder <0,  0, 0>, <5, 0, 0>, 1, 0.7,
  1217.          cylinder <1, -3, 0>, <3, 2, 0>, 1, 1.4,
  1218.          sphere <3, -0.8, 0>, 1, 1,
  1219.          sphere <4,  0.5, 0>, 1, 1,
  1220.          sphere <1,  1,   0>, 1, 1,
  1221.          sphere <1,  1.5, 0>, 1, 1,
  1222.          sphere <1,  2.7, 0>, 1, 1
  1223.  
  1224.       texture {
  1225.          surface {
  1226.             color red
  1227.             ambient 0.2
  1228.             diffuse 0.8
  1229.             specular white, 1
  1230.             microfacet Phong 5
  1231.             }
  1232.          }
  1233.    }
  1234.  
  1235. Note: since a blob is essentially a collection of 4th order polynomials, it
  1236. is possible to specify which quartic root solver to use.  See section 2.3.2.12,
  1237. "Polynomial surface" for a description of the "root_solver" statement.
  1238.  
  1239. Sample file: blob.pi
  1240.  
  1241. 2.3.2.3 Box
  1242.  
  1243. A box is defined in terms of two diagonally opposite corners.  Using the
  1244. box primitive will give the same result as the CSG intersection of six planes,
  1245. but is quite a bit faster.
  1246.  
  1247. The format of the declaration is:
  1248.  
  1249.    box <x0, y0, z0>, <x1, y1, z1>
  1250.  
  1251. Usually the convention is that the first point is the front-lower-left point
  1252. and the second is the back-upper-right point.  The following declaration is four
  1253. boxes stacked on top of each other:
  1254.  
  1255.    define pyramid
  1256.    object {
  1257.         object { box <-1, 3, -1>, <1, 4, 1> }
  1258.       + object { box <-2, 2, -2>, <2, 3, 2> }
  1259.       + object { box <-3, 1, -3>, <3, 2, 3> }
  1260.       + object { box <-4, 0, -4>, <4, 1, 4> }
  1261.       matte_blue
  1262.       }
  1263.  
  1264. Sample file: boxes.pi
  1265.  
  1266. 2.3.2.4 Cone
  1267.  
  1268. A cone is defined in terms of a base point, an apex point, and the radii at
  1269. those two points.  Note that cones are not closed.
  1270.  
  1271. The format of the declaration is:
  1272.  
  1273.    cone <x0, y0, z0>, r0, <x1, y1, z1>, r1
  1274.  
  1275. An example declaration of a cone is:
  1276.  
  1277.      object {
  1278.         cone <0, 0, 0>, 4, <4, 0, 0>, 0
  1279.         shiny_red
  1280.         }
  1281.  
  1282. Sample file: cone.pi
  1283.  
  1284. 2.3.2.5 Cylinder
  1285.  
  1286. A cylinder is defined in terms of a bottom point, a top point, and its radius.
  1287. Note that cylinders are not closed.
  1288.  
  1289. The format of the declaration is:
  1290.  
  1291.    cylinder <x0, y0, z0>, <x1, y1, z1>, r
  1292.  
  1293. An example of a cylinder is:
  1294.  
  1295.    object {
  1296.       cylinder <-3, -2, 0>, <0, 1, 3>, 0.5
  1297.       shiny_red
  1298.       }
  1299.  
  1300. Sample file: cylinder.pi
  1301.  
  1302. 2.3.2.6 Disc
  1303.  
  1304. A disc is defined in terms of a center a normal and either a radius, or using
  1305. an inner radius and an outer radius.  If only one radius is given, then the disc
  1306. has the appearance of a (very) flat coin.  If two radii are given, then the disc
  1307. takes the shape of an annulus (washer) where the disc extends from the first
  1308. radius to the second radius.  Typical uses for discs are as caps for cones and
  1309. cylinders, or as ground planes (using a really big radius).
  1310.  
  1311. The format of the declaration is:
  1312.  
  1313.    disc <cx, cy, cz>, <nx, ny, nz>, r
  1314. or
  1315.    disc <cx, cy, cz>, <nx, ny, nz>, ir, or
  1316.  
  1317. The center vector <cx,cy,cz> defines where the center of the disc is located, the
  1318. normal vector <nx,ny,nz> defines the direction that is perpendicular to the disc.
  1319. i.e. a disc having the center <0,0,0> and the normal <0,1,0> would put the disc in
  1320. the x-z plane with the y-axis coming straight out of the center.
  1321.  
  1322. An example of a disc is:
  1323.  
  1324.    object {
  1325.       disc <0, 2, 0>, <0, 1, 0>, 3
  1326.       rotate <-30, 20, 0>
  1327.       shiny_red
  1328.       }
  1329.  
  1330. Note: a disc is infinitely thin.  If you look at it edge-on it will disappear.
  1331.  
  1332. Sample file: disc.pi
  1333.  
  1334. 2.3.2.7 Implicit Surface
  1335.  
  1336. The format of the declaration is:
  1337.  
  1338.    function f(x,y,z)
  1339.  
  1340. The function f(x,y,z) may be any algebraic expression composed of the variables:
  1341. x, y, z, a numerical value (i.e. 0.5), the operators: +, -, *, /, ^, and the
  1342. functions:  cos, cosh, exp, fabs, ln, log, sin, sinh, tan, tanh.  The code
  1343. is not particularly fast, not is it totally accurate, however the capability
  1344. to ray-trace such a wide class of functions by a SW program is (I believe)
  1345. unique to Polyray.
  1346.  
  1347. The distance along the ray that solutions will be found in are determined by
  1348. the following:
  1349.  
  1350.    o If there is a bounding shape, then the first hit and last hit of the
  1351.      current ray and the bounding shape will be used as the search interval.
  1352.  
  1353.    o If there is no bounding shape then the interval from 0.01 to 100 will be
  1354.      used.
  1355.  
  1356.    o Solutions must be more than 1.0e-4 units distant from each other.
  1357.  
  1358. Note: the absolute value can be written with vertical bars, i.e. |x|^0.75.
  1359.  
  1360. The following object is taken from "sombrero.pi" and is a surface that
  1361. looks very much like diminishing ripples on the surface of water.
  1362.  
  1363.    define a_const 1.0
  1364.    define b_const 2.0
  1365.    define c_const 3.0
  1366.    define two_pi_a 2.0 * 3.14159265358 * a_const
  1367.  
  1368.    # Define a diminishing cosine surface (sombrero)
  1369.    object {
  1370.       function y - c_const * cos(two_pi_a * sqrt(x^2 + z^2)) *
  1371.                              exp(-b_const * sqrt(x^2 + z^2))
  1372.       matte_red
  1373.       bounds object { box <-4, -4, -4>, <4, 4, 4> }
  1374.       }
  1375.  
  1376. Sample files: helix.pi, sinsurf.pi, sombrero.pi, superq.pi, zonal.pi
  1377.  
  1378. 2.3.2.8 Height Field
  1379.  
  1380. There are two ways that height fields can be specified, either by using data
  1381. stored in a Targa file, or using an implicit function of the form y = f(x, z).
  1382.  
  1383. The default orientation of a height field is that the entire field lies in
  1384. the square 0 <= x <= 1, 0 <= z <= 1.  File based height fields are always in
  1385. this orientation, implicit height fields can optionally be defined over a
  1386. different area of the x-z plane.  The height value is used for y.
  1387.  
  1388. 2.3.2.8.1 File Based Height Fields
  1389.  
  1390. Height fields data can be read from a Targa format file.  The only formats
  1391. currently supported are 16 and 24 bit uncompressed.
  1392.  
  1393.  
  1394. The format of the declaration is:
  1395.  
  1396.    height_field "filename"
  1397.  
  1398. The sample program "wake.c" generates a Targa file that simulates the wake
  1399. behind a boat.
  1400.  
  1401. Sample file: wake.pi (requires that "wave.tga" be generated by "wake.c")
  1402.  
  1403. The way the pixel values of the file are interpreted are:
  1404.  
  1405. 2.3.2.8.1.1 16 Bit Format
  1406.  
  1407. Each pixel in the file is represented by two bytes, low then high.  The
  1408. high component defines the integer component of the height, the low
  1409. component holds the fractional part scaled by 255. The entire value is offset
  1410. by 128 to compensate for the unsigned nature of the storage bytes.
  1411. As an example the values  high = 140, low = 37 would be translated to the
  1412. height:
  1413.  
  1414.    (140 + 37 / 256) - 128 = 12.144
  1415.  
  1416. similarily if you are generating a Targa file to use in Polyray, given
  1417. a height, add 128 to the height, extract the integer component, then
  1418. extract the scaled fractional component.  The following code fragment shows
  1419. a way of generating the low and high bytes from a floating point number.
  1420.  
  1421.          unsigned char low, high;
  1422.          float height;
  1423.          FILE *height_file;
  1424.  
  1425.          ...
  1426.  
  1427.          height += 128.0;
  1428.          high = (unsigned char)height;
  1429.          height -= (float)high;
  1430.          low = (unsigned char)(256.0 * height);
  1431.          fputc(low, height_file);
  1432.          fputc(high, height_file);
  1433.  
  1434.  
  1435.  
  1436. 2.3.2.8.1.2 24 Bit Format
  1437.  
  1438. The red component defines the integer component of the height, the green
  1439. component holds the fractional part scaled by 255, the blue component is
  1440. ignored.  The entire value is offset by 128 to compensate for the unsigned
  1441. nature of the RGB  values.  As an example the values  r = 140, g = 37, and
  1442. b = 0 would be translated to the height:
  1443.  
  1444.    (140 + 37 / 256) - 128 = 12.144
  1445.  
  1446. similarily if you are generating a Targa file to use in Polyray, given
  1447. a height, add 128 to the height, extract the integer component, then
  1448. extract the scaled fractional component.  The following code fragment shows
  1449. a way of generating the RGB components from a floating point number.
  1450.  
  1451.          unsigned char r, g, b;
  1452.          float height;
  1453.          FILE *height_file;
  1454.  
  1455.          ...
  1456.  
  1457.          height += 128.0;
  1458.          r = (unsigned char)height;
  1459.          height -= (float)r;
  1460.          g = (unsigned char)(256.0 * height);
  1461.          b = 0;
  1462.          fputc(b, height_file);
  1463.          fputc(g, height_file);
  1464.          fputc(r, height_file);
  1465.  
  1466.  
  1467. 2.3.2.8.2 Implicit Height Fields
  1468.  
  1469. Another way to define height fields is by evaluating a mathematical function
  1470. over a grid.  Given a function y = f(x, z), Polyray will evaluate the function
  1471. over a specified area and generate a height field based on the function.
  1472. This method can be used to generate images of many sorts of functions that are
  1473. not easily representable by collections of simpler primitives.
  1474.  
  1475. The valid formats of the declaration are:
  1476.  
  1477.    height_fn xsize, zsize, min_x, max_x, min_z, max_z, expression
  1478.    height_fn xsize, zsize, expression
  1479.  
  1480. If the four values min_x, max_x, min_z, and max_z are not defined then
  1481. the default square 0 <= x <= 1, 0 <= z <= 1 will be used.
  1482.  
  1483. For example,
  1484.  
  1485.    # Define constants for the sombrero function
  1486.    define a_const 1.0
  1487.    define b_const 2.0
  1488.    define c_const 3.0
  1489.    define two_pi_a 2.0 * 3.14159265358 * a_const
  1490.  
  1491.    # Define a diminishing cosine surface (sombrero)
  1492.    object {
  1493.       height_fn 80, 80, -4, 4, -4, 4,
  1494.          c_const * cos(two_pi_a * sqrt(x^2 + z^2)) *
  1495.                    exp(-b_const * sqrt(x^2 + z^2))
  1496.       shiny_red
  1497.       }
  1498.  
  1499. will build a height field 80x80, covering the area from -4 <= x <= 4, and
  1500. -4 <= z <= 4.  (Note that the boundary defined by the limits of x, and z does
  1501. not have to be square, only the grid.)
  1502.  
  1503. Compare the run-time performance and visual quality of the sombrero function
  1504. as defined in "sombfn.pi" with the sombrero function as defined in
  1505. "sombrero.pi".  The former uses a height field representation and renders quite
  1506. fast.  The latter uses a very general function representation and gives smoother
  1507. but very slow results.
  1508.  
  1509. Sample file: sombfn.pi, sinfn.pi
  1510.  
  1511. 2.3.2.9 Lathe surfaces
  1512.  
  1513. A lathe surface is a polygon that has been revolved about the y-axis.  This
  1514. surface allows you to build objects that are symmetric about an axis, simply
  1515. by defining 2D points.
  1516.  
  1517. The format of the declaration is:
  1518.  
  1519.     lathe type, direction, total_vertices,
  1520.        <vert1.x,vert1.y,vert1.z>
  1521.        [, <vert2.x, vert2.y, vert2.z>]
  1522.        [, etc. for total_vertices vertices]
  1523.  
  1524. The value of "type" is either 1, or 2.  If the value is 1, then the surface
  1525. will simply revolve the line segments.  If the value is 2, then the surface
  1526. will be represented by a spline that approximates the line segments that
  1527. were given.  A lathe surface of type 2 is a very good way to smooth off
  1528. corners in a set of line segments.
  1529.  
  1530. The value of the vector "direction" is used to change the orientation of the
  1531. lathe.  For a lathe surface that goes straight up and down the y-axis, use
  1532. <0, 1, 0> for "direction.  For a lathe surface that lies on the x-axis, you
  1533. would use <1, 0, 0> for the direction.
  1534.  
  1535. Sample file: lathe1.pi, lathe2.pi
  1536.  
  1537. Note that CSG will really only work correctly if you close the lathe - that
  1538. is either make the end point of the lathe the same as the start point, or
  1539. make the x-value of the start and end points equal zero.  Lathes, unlike
  1540. polygons are not automatically closed by Polyray.
  1541.  
  1542. Note: since a splined lathe surface (type = 2) is a 4th order polynomial, it is
  1543. possible to specify which quartic root solver to use.  See section 2.3.2.12,
  1544. "Polynomial surface" for a description of the "root_solver" statement.
  1545.  
  1546. 2.3.2.10 Parabola
  1547.  
  1548. A parabola is defined in terms of a bottom point, a top point, and its radius
  1549. at the top.
  1550.  
  1551. The format of the declaration is:
  1552.  
  1553.    parabola <x0, y0, z0>, <x1, y1, z1>, r
  1554.  
  1555. The vector <x0,y0,z0> defines the "top" of the parabola - the part that comes
  1556. to a point.  The vector <x1,y1,z1> defines the "bottom" of the parabola, the
  1557. width of the parabola at this point is "r".
  1558.  
  1559. An example of a parabola declaration is:
  1560.  
  1561.    object {
  1562.       parabola <0, 6, 0>, <0, 0, 0>, 3
  1563.       translate <16, 0, 16>
  1564.       steel_blue
  1565.       }
  1566.  
  1567. This is sort of like a salt shaker shape with a rounded top and the base on
  1568. the x-z plane.
  1569.  
  1570. 2.3.2.11 Polygon
  1571.  
  1572. Although polygons are not very interesting mathematically, there are many
  1573. sorts of objects that are much easier to represent with polygons.  Polyray
  1574. assumes that all polygons are closed and automatically adds a side from the
  1575. last vertex to the first vertex.
  1576.  
  1577. The format of the declaration is:
  1578.  
  1579.     polygon total_vertices,
  1580.        <vert1.x,vert1.y,vert1.z>
  1581.        [, <vert2.x, vert2.y, vert2.z>]
  1582.        [, etc. for total_vertices vertices]
  1583.  
  1584. As with the sphere, note the comma separating each vertex of the
  1585. polygon.
  1586.  
  1587. I use polygons as a floor in a lot of images.  They are a little slower than
  1588. the corresponding plane, but for scan conversion they are a lot easier to
  1589. handle.  An example of a checkered floor made from a polygon is:
  1590.  
  1591.    object {
  1592.       polygon 4, <-20, 0, -20>, <-20, 0, 20>, <20, 0, 20>, <20, 0, -20>
  1593.       texture {
  1594.          checker matte_white, matte_black
  1595.          translate <0, -0.1, 0>
  1596.          scale <2, 1, 2>
  1597.          }
  1598.       }
  1599.  
  1600. 2.3.2.12 Polynomial surface
  1601.  
  1602. The format of the declaration is:
  1603.  
  1604.    polynomial f(x,y,z)
  1605.  
  1606. The function f(x,y,z) must be a simple polynomial, i.e. x^2+y^2+z^2-1.0 is
  1607. the definition of a sphere of radius 1 centered at (0,0,0).  See section 4.1 for
  1608. a little more detail on restrictions on the form of the polynomial.
  1609.  
  1610. For quartic equations, there are three available ways to solve for roots, by
  1611. specifying which one is desired, it is possible to tune for quality or speed.
  1612. The method of Ferrari is the fastest, but also the most numerically unstable.
  1613. By default the method of Vieta is used.  Sturm sequences (which are the slowest)
  1614. should be used where the highest quality is desired.
  1615.  
  1616. The declaration of which root solver to use takes one of the forms:
  1617.  
  1618.    root_solver Ferrari
  1619.    root_solver Vieta
  1620.    root_solver Sturm
  1621.  
  1622. (Capitalization is important - these are proper nouns after all.)
  1623.  
  1624. Note: due to unavoidable numerical inaccuracies, not all polynomial surfaces
  1625. will render correctly from all directions.
  1626.  
  1627. The following example, taken from "devil.pi" defines a quartic
  1628. polynomial.  The use of bounding and clipping objects are to trim
  1629. uninteresting parts of the surface, as well as to help the scan conversion
  1630. routines to identify where to look for the surface.
  1631.  
  1632.    // Variant of a devil's curve in 3-space.  This figure has a top and
  1633.    // bottom part that are very similar to a hyperboloid of one sheet,
  1634.    // however the central region is pinched in the middle leaving two
  1635.    // teardrop shaped holes.
  1636.    object {
  1637.       polynomial x^4 + 2*x^2*z^2 - 0.36*x^2 - y^4 + 0.25*y^2 + z^4
  1638.       root_solver Ferrari
  1639.       bounds  object { box <-2, -2, -0.5>, <2, 2, 0.5> }
  1640.       clips  object { box <-2, -2, -0.5>, <2, 2, 0.5> }
  1641.       rotate <10, 20, 0>
  1642.       translate <0, 3, -10>
  1643.       shiny_red
  1644.       }
  1645.  
  1646. Note: as the order of the polynomial goes up, the numerical accuracy required to
  1647. render the surface correctly also goes up.  One problem that starts to rear its
  1648. ugly head starting at aroung 3rd to 4th order equations is a problem with
  1649. determining shadows correctly.  The result is black spots on the surface.  You can
  1650. east this problem to a certain extent by making the value of "shadow_tolerance"
  1651. larger.  For 4th and higher equations, you will want to use a value of at least
  1652. 0.05, rather than the default 0.001.
  1653.  
  1654. Sample file: torus.pi, many others
  1655.  
  1656. 2.3.2.13 Spheres
  1657.  
  1658. Spheres are the simplest 3D object to render and a sphere primitive enjoys
  1659. a speed advantage over most other primitives.
  1660.  
  1661. The format of the declaration is:
  1662.  
  1663.     sphere <center.x, center.y, center.z>, radius
  1664.  
  1665. Note the comma after the center vector, it really is necessary.
  1666.  
  1667. My basic benchmark file is a single sphere, illuminated by a single light.
  1668. The definition of the sphere is:
  1669.  
  1670.    object {
  1671.       sphere <0, 0, 0>, 2
  1672.       shiny_red
  1673.       }
  1674.  
  1675. Sample file: sphere.pi
  1676.  
  1677. 2.3.2.14 Sweep surface
  1678.  
  1679. A sweep surface, also refered to as an extruded surface, is a polygon
  1680. that has been swept along a given direction.  It can be used to make
  1681. multi-sided beams, or to create ribbon-like objects.
  1682.  
  1683. The format of the declaration is:
  1684.  
  1685.     sweep type, direction, total_vertices,
  1686.        <vert1.x,vert1.y,vert1.z>
  1687.        [, <vert2.x, vert2.y, vert2.z>]
  1688.        [, etc. for total_vertices vertices]
  1689.  
  1690. The value of "type" is either 1, or 2.  If the value is 1, then the surface
  1691. will be a set of connected squares.  If the value is 2, then the surface
  1692. will be represented by a spline that approximates the line segments that
  1693. were given.
  1694.  
  1695. The value of the vector "direction" is used to change the orientation of the
  1696. sweep.  For a sweep surface that is extruded straight up and down the y-axis, use
  1697. <0, 1, 0> for "direction.  The size of the vector "direction" will also affect
  1698. the amount of extrusion, i.e. if |direction| = 2, then the extrusion will be two
  1699. units in that direction.
  1700.  
  1701. An example of a sweep surface is:
  1702.  
  1703.    // Sweep made from connected quadratic splines.
  1704.    object {
  1705.       sweep 2, <0, 2, 0>, 16,
  1706.          <0, 0>, <0, 1>, <-1, 1>, <-1, -1>, <2, -1>, <2, 3>,
  1707.          <-4, 3>, <-4, -4>, <4, -4>, <4, -11>, <-2, -11>,
  1708.          <-2, -7>, <2, -7>, <2, -9>, <0, -9>, <0, -8>
  1709.       translate <0, 0, -4>
  1710.       scale <1, 0.5, 1>
  1711.       rotate <0,-45, 0>
  1712.       translate <10, 0, -18>
  1713.       shiny_yellow
  1714.       }
  1715.  
  1716.  
  1717. Sample file: sweep1.pi, sweep2.pi
  1718.  
  1719. Note that CSG will really only work correctly if you close the sweep - that
  1720. is make the end point of the sweep the same as the start point.  Sweeps, unlike
  1721. polygons are not automatically closed by Polyray.
  1722.  
  1723. 2.3.2.15 Torus
  1724.  
  1725. The torus primitive is a doughnut shaped surface that is defined by a center
  1726. point, the distance from the center point to the middle of the ring of the
  1727. doughnut, the radius of the ring of the doughnut, and the orientation of
  1728. the surface.
  1729.  
  1730. The format of the declaration is:
  1731.  
  1732.     torus r0, r1, <center.x, center.y, center.z>, <dir.x, dir.y, dir.z>
  1733.  
  1734.  
  1735. As an example, a torus that has major radius 1, minor radius 0.4, and is
  1736. oriented so that the ring lies in the x-z plane would be declared as:
  1737.  
  1738.    object {
  1739.       torus 1, 0.4, <0, 0, 0>, <0, 1, 0>
  1740.       shiny_red
  1741.       }
  1742.  
  1743. Note: since a torus is a 4th order polynomial, it is possible to specify which
  1744. quartic root solver to use.  See section 2.3.2.12, "Polynomial surface" for a
  1745. description of the "root_solver" statement.
  1746.  
  1747. Sample file: torus.pi
  1748.  
  1749. 2.3.2.15 Triangular patches
  1750.  
  1751. A triangular patch is defined by a set of vertices and their normals.
  1752. When calculating shading information for a triangular patch, the normal
  1753. information is used to interpolate the final normal from the intersection
  1754. point to produce a smooth shaded triangle.
  1755.  
  1756. The format of the declaration is:
  1757.  
  1758.     patch <vert1.x,vert1.y,vert1.z>, <norm1.x,norm1.y,norm1.z>,
  1759.           <vert2.x,vert2.y,vert2.z>, <norm2.x,norm2.y,norm2.z>,
  1760.           <vert3.x,vert3.y,vert3.z>, <norm3.x,norm3.y,norm3.z>
  1761.  
  1762. Smooth patch data is usually generated as the output of another program.
  1763.  
  1764. 2.3.3 Constructive Solid Geometry (CSG)
  1765.  
  1766. Objects can be defined in terms of the union, intersection, and inverse of
  1767. other objects.  The operations and the symbols used are:
  1768.  
  1769.    csgexper + csgexper  - Union
  1770.    csgexper * csgexper  - Intersection
  1771.    csgexper - csgexper  - Difference
  1772.    ~csgexper            - Inverse
  1773.    (csgexper)           - Parenthesised expression
  1774.  
  1775. Note that intersection and difference require a clear inside and outside.  Not
  1776. all primitives have well defined sides.  Those that do are:
  1777.  
  1778.    Spheres, Boxes, Polynomials, Blobs, and Functions.
  1779.  
  1780. Other surfaces that do not always have a clear inside/outside, but work
  1781. reasonably well in CSG intersections are:
  1782.  
  1783.    Cylinders, Cones, Discs, Lathes, Parabola, Polygons, and Sweeps.
  1784.  
  1785. Using Cylinders, Cones, and Parabolas works correctly, but the open ends of
  1786. these surfaces will also be open in the resulting CSG.  To close them off you
  1787. can use a disc shape.
  1788.  
  1789. Using Discs, and Polygons in a CSG is really the same as doing a CSG with
  1790. the plane that they lie in.  If fact, a large disc is an excellent choice for
  1791. clipping or intersecting an object, as the inside/outside test is very fast.
  1792.  
  1793. Lathes, and Sweeps use Jordan's rule to determine if a point is inside.  This
  1794. means that given a test point, if a line from that point to infinity crosses
  1795. the surface an odd number of times, then the point is inside.  The net result
  1796. is that if the lathe (or sweep) is not closed, then you may get odd results
  1797. in a CSG intersection (or difference). 
  1798.  
  1799. Height fields don't work well with CSG.
  1800.  
  1801. As an example, the following object is a sphere of radius 1 with a hole
  1802. of radius 0.5 through the middle:
  1803.  
  1804.    define cylinder_z object { cylinder <0, 0, -5>, <0, 0, 5>, 0.5 }
  1805.    define unit_sphere object { sphere <0, 0, 0>, 1 }
  1806.  
  1807.    // Define a CSG shape by deleting a cylinder from a sphere
  1808.    object {
  1809.       unit_sphere - cylinder_z
  1810.       shiny_red
  1811.       }
  1812.  
  1813. Sample files: lens.pi, polytope.pi
  1814.  
  1815. 2.3.4 Bounding Slabs
  1816.  
  1817. The format of a bounding slab declaration is:
  1818.  
  1819.     bounding_slab <dir.x, dir.y, dir.z>
  1820.  
  1821. This declaration will cause Polyray to attempt to sort the objects in the scene
  1822. along the given direction.  For scenes with many objects, the typical declarations
  1823. would be:
  1824.  
  1825.    bounding_slab <1, 0, 0>
  1826.    bounding_slab <0, 1, 0>
  1827.    bounding_slab <0, 0, 1>
  1828.  
  1829. These declarations will cause Polyray to try to sort all top level objects along
  1830. the x, y, and z directions.  Note that this sorting operation can lead to the
  1831. generation of many new objects that will contain the ones defined in the data
  1832. file.  You may need to boost the allowed number of primitives by modifying
  1833. the "max_prims" value in the file "polyray.ini".
  1834.  
  1835. Note: there are still bugs in the bounding slab process.  In particular shadows
  1836. are sometimes incorrect, objects that should be blocking the path to the light
  1837. seem to sometimes get overlooked.
  1838.  
  1839. Bounding slabs work best when there are many small objects, and when the objects
  1840. are oriented in such a way that they can be separated by the slabs.
  1841.  
  1842. Notes:
  1843.  
  1844.    1) All of the primitives except implicit functions and polynomial surfaces
  1845.       will have bounding information automatically generated.  For those types
  1846.       of surfaces, there must be a bounding object that contains a bounded
  1847.       primitive in order to determine the bounding information.
  1848.       
  1849.    2) CSG that involves either difference operations ("-") or inverse operations
  1850.       ("~") can cause the automatic bounding operation to screw up.  It is
  1851.       fairly rare, and for those cases you can improve the result by adding a
  1852.       bounding object to the CSG.  The bounds of the bounding object will be
  1853.       used rather than trying to guess at bounding information using the
  1854.       individual parts of the CSG.
  1855.  
  1856. 2.4 Color and lighting
  1857.  
  1858. The color space used in polyray is RGB, with values of each component
  1859. specified as a value from 0 -> 1.  The way the color and shading of surfaces
  1860. is specified is described in the following sections.
  1861.  
  1862. RGB colors are defined as either a three component vector, such as
  1863. <0.6, 0.196078, 0.8>, or as one of the X11R3 named colors (which for the
  1864. value given is DarkOrchid).  One of these days when I feel like typing and
  1865. not thinking (or if I find them on line), I'll put in the X11R4 colors.
  1866.  
  1867. The coloring of objects is determined by the interaction of lights, the shape
  1868. of the surface it is striking, and the characteristics of the surface itself.
  1869.  
  1870. 2.4.1 Light sources
  1871.  
  1872. Light sources are either simple positional light sources or spot lights.
  1873.  
  1874. Note:  After the input file has been read, the brightness of all light sources
  1875. is divided by sqrt(# of lights).  This is the way mtv did it & for now will be
  1876. left that way.  (Defining RGB as smaller values than 1.0 will lead to dimmer
  1877. lights also...)
  1878.  
  1879. 2.4.1.1 Positional Lights
  1880.  
  1881. A positional light is defined by its RGB color and its XYZ position.
  1882.  
  1883. The format of the declaration is:
  1884.  
  1885.     light color, location
  1886.     light location
  1887.     
  1888. The second declaration will use white as the color.
  1889.  
  1890. 2.4.1.2 Spot Lights
  1891.  
  1892. The format of the declaration is:
  1893.  
  1894.     spot_light color, location, pointed_at, Tightness, Angle, Falloff
  1895.     spot_light location, pointed_at
  1896.  
  1897. The vector "location" defines the position of the spot light, the vector
  1898. "pointed_at" defines the point at which the spot light is directed.  The
  1899. optional components are:
  1900.  
  1901.    color        - The color of the spotlight
  1902.    Tightness    - The power function used to determine the shape of the hot spot
  1903.    Angle        - The angle (int degrees) of the full effect of the spot light
  1904.    Falloff      - A larger angle at which the amount of light falls to nothing
  1905.  
  1906. A sample declaration is:
  1907.  
  1908.    spot_light white, <10,10,0>, <3,0,0>, 3, 5, 20
  1909.  
  1910. Sample file: spot0.pi
  1911.  
  1912. 2.4.2 Background color
  1913.  
  1914. The background color is the one used if the current ray does not strike any
  1915. objects.  The color can be any vector expression, although is usually a simple
  1916. RGB color value.
  1917.  
  1918. The format of the declaration is:
  1919.  
  1920.     background <R,G,B>
  1921.  or
  1922.     background color
  1923.  
  1924. If no background color is set black will be used.
  1925.  
  1926. An interesting trick that can be performed with the background is to use
  1927. an image map as the background color (it is also a way to translate from
  1928. one Targa format to another).  The way this can be done is:
  1929.  
  1930. background planar_imagemap(image("test1.tga", P)
  1931.  
  1932. 2.4.3 Textures
  1933.  
  1934. Polyray supports a few simple procedural textures: a standard shading model,
  1935. a checker texture, a hexagon texture, a noise texture, and a radial texture.
  1936. In addition, a very flexible (although slower) functional texture is supported.
  1937. The general syntax of a texture is:
  1938.  
  1939.    texture { [texture declaration] }
  1940. or
  1941.    texture_sym
  1942.  
  1943. Where "texture_sym" is a previously defined texture declaration.
  1944.  
  1945. 2.4.3.1 Procedural Textures
  1946.  
  1947. 2.4.3.1.1 Standard Shading Model
  1948.  
  1949. Unlike many other ray-tracers, a surface does not have a single color that is
  1950. used for all of the components of the shading model.  Instead a number of
  1951. characteristics of the surface must be defined (with a matte white
  1952. being the default).
  1953.  
  1954. A surface declaration has the form:
  1955.  
  1956.      surface {
  1957.         [ surface definitions ]
  1958.         }
  1959.  
  1960. For example, the following declaration is a red surface with a white highlight,
  1961. corresponding to the often seen "plastic" texture:
  1962.  
  1963.    define shiny_red
  1964.    texture {
  1965.       surface {
  1966.          ambient red, 0.2
  1967.          diffuse red, 0.6
  1968.          specular white, 0.8
  1969.          microfacet Reitz 10
  1970.          }
  1971.       }
  1972.  
  1973. The allowed surface characteristics that can be defined are:
  1974.  
  1975.    ambient              - Light given off by the surface
  1976.    diffuse              - Light reflected in all directions
  1977.    specular             - Amount and color of specular highlights
  1978.    reflection           - Reflectivity of the surface
  1979.    transmission         - Amount and color of refracted light
  1980.    microfacet           - Specular lighting model (see below)
  1981.  
  1982. The lighting equation used is (in somewhat simplified terms):
  1983.  
  1984.    L = ambient + diffuse + specular + reflected + transmitted, or
  1985.  
  1986.    L = Ka + Kd * (l1 + l2 + ...) + Ks * (l1 + l2 + ...) + Kr + Kt
  1987.  
  1988. Where l1, l2, ... are the lights, Ka is the ambient term, Kd is the diffuse
  1989. term, Ks is the specular term, Kr is the reflective term, and Kt it the
  1990. transmitted (refractive) term. Each of these terms has a scale value and
  1991. a filter value (the filter defaults to white/clear if unspecified).
  1992.  
  1993. See the file "colors.inc" for a number of declarations of surface
  1994. characteristics, including: mirror, glass, shiny, and matte.
  1995.  
  1996. For lots of detail on lighting models, and the theory behind how color is
  1997. used in computer generated images, run (don't walk) down to your local
  1998. computer bookstore and get:
  1999.  
  2000.       "Illumination and Color in Computer Generated Imagery"
  2001.       Roy Hall, 1989
  2002.       Springer Verlag
  2003.  
  2004. Source code in the back of that book was the inspiration for the microfacet
  2005. distribution models implemented for polyray.
  2006.  
  2007. Note that you don't really have to specify all of the color components if you
  2008. don't want to.  If the color of a particular part of the surface declaration
  2009. is not defined, then the value of the "color" component will be examined to
  2010. see if it was declared.  If so, then that color will be used as the filter.  As
  2011. an example, the declaration above could also be written as:
  2012.  
  2013.    define shiny_red
  2014.    texture {
  2015.       surface {
  2016.          color red
  2017.          ambient 0.2
  2018.          diffuse 0.6
  2019.          specular white, 0.8
  2020.          microfacet Reitz 10
  2021.          }
  2022.       }
  2023.  
  2024. 2.4.3.1.1.1 Ambient light
  2025.  
  2026. Ambient lighting is the light given off by the surface itself.
  2027.  
  2028. The format of the declaration is:
  2029.  
  2030.     ambient color, scale
  2031.     ambient scale
  2032.  
  2033. As always, color indicates either an RGB triple like <1.0,0.7,0.9>, or a named
  2034. color.  scale gives the amount of contribution that ambient gives to the
  2035. overall amount light coming from the pixel.  The scale values should lie in
  2036. the range 0.0 -> 1.0
  2037.  
  2038. 2.4.3.1.1.2 Diffuse light
  2039.  
  2040. Diffuse lighting is the light given off by the surface under stimulation by
  2041. a light source.
  2042.  
  2043. The format of the declaration is:
  2044.  
  2045.     diffuse color, scale
  2046.     diffuse scale
  2047.  
  2048. The only information used for diffuse calculations is the angle of incidence
  2049. of the light on the surface.
  2050.  
  2051. 2.4.3.1.1.3 Specular highlights
  2052.  
  2053. The format of the declaration is:
  2054.  
  2055.    specular color, scale
  2056.    specular scale
  2057.  
  2058. The means of calculating specular highlights is by default the Phong model.
  2059. Other models are selected through the Microfacet distribution declaration.
  2060.  
  2061. 2.4.3.1.1.4 Reflected light
  2062.  
  2063. Reflected light is the color of whatever lies in the reflected direction
  2064. as calculated by the relationship of the view angle and the normal to the
  2065. surface.
  2066.  
  2067. The format of the declaration is:
  2068.  
  2069.    reflection scale
  2070.    reflection color, scale
  2071.  
  2072. Typically, only the scale factor is included in the reflection declaration,
  2073. this corresponds to all colors being reflected with intensity porportional
  2074. to the scale.  A color filter is allowed in the reflection definition, and
  2075. this allows the modification of the color being reflected (I'm not sure if
  2076. this is useful, but I included it anyway).
  2077.  
  2078. 2.4.3.1.1.5 Transmitted light
  2079.  
  2080. Transmitted light is the color of whatever lies in the refracted direction
  2081. as calculated by the relationship of the view angle, the normal to the
  2082. surface, and the index of refraction of the material.
  2083.  
  2084. The format of the declaration is:
  2085.  
  2086.    transmit scale, ior
  2087.    transmit color, scale, ior
  2088.  
  2089. Typically, only the scale factor is included in the transmitted declaration,
  2090. this corresponds to all colors being transmitted with intensity porportional
  2091. to the scale.  A color filter is allowed in the transmitted definition, and
  2092. this allows the modification of the color being transmitted by making the
  2093. transmission filter different from the color of the surface itself.
  2094.  
  2095. It is possible to have surfaces with colors very different than the one closest
  2096. to the eye become apparent.  (See "gsphere.pi" for an example, a red sphere is
  2097. in the foreground, a green sphere and a blue sphere behind.  The specular
  2098. highlights of the red sphere go to yellow, and blue light is transmitted
  2099. through the red sphere.)
  2100.  
  2101. A more complex file is "lens.pi" in which two convex lenses are lined up
  2102. in front of the viewer.  The magnified view of part of a grid of colored
  2103. balls is very apparent in the front lens.
  2104.  
  2105. 2.4.3.1.1.6 Microfacet distribution
  2106.  
  2107. The microfact distribution is a function that determines how the specular
  2108. highlighting is calculated for an object.
  2109.  
  2110. The format of the declaration is:
  2111.  
  2112.    microfacet Distribution_name falloff_angle
  2113.    microfacet falloff_angle
  2114.  
  2115. The distribution name is one of: Blinn, Cook, Gaussian, Phong, Reitz.  The
  2116. falloff angle is the angle at which the specular highlight falls to 50% of
  2117. its maximum intensity.  (The smaller the falloff angle, the sharper the
  2118. highlight.)  If a microfacet name is not given, then the Phong model is
  2119. used.
  2120.  
  2121. The falloff angle must be specified in degrees, with values in the range
  2122. 0 to 90.  The falloff angle corresponds to the roughness of the surface, the
  2123. smaller the angle, the smoother the surface.  A very wide falloff angle will
  2124. give the same sort of shading that diffuse shading gives.
  2125.  
  2126. Note: as stated before, look at the book by Hall.  I have found falloff values
  2127. of 5-10 degrees to give nice tight highlights.  Using falloff angle may seem a
  2128. bit backwards from other raytracers, which typically use a value defining
  2129. the power of a cosine function to define highlight size.  When using a power
  2130. value, the higher the power, the smaller the highlight.  Using angles seems
  2131. a little tidier since the smaller the angle, the smaller the highlight.
  2132.  
  2133. 2.4.3.1.2 Checker
  2134.  
  2135. the checker texture has the form:
  2136.  
  2137.    texture {
  2138.       checker texture1, texture2
  2139.       }
  2140.  
  2141. where texture1 and texture2 are texture declarations (or texture constants).
  2142.  
  2143. A standard sort of checkered plane can be defined with the following:
  2144.  
  2145.    # Define a matte red surface
  2146.    define matte_red
  2147.    texture {
  2148.       surface {
  2149.          ambient red, 0.1
  2150.          diffuse red, 0.5
  2151.          }
  2152.       }
  2153.  
  2154.    # Define a matte blue surface
  2155.    define matte_blue
  2156.    texture {
  2157.       surface {
  2158.          ambient blue, 0.2
  2159.          diffuse blue, 0.8
  2160.          }
  2161.       }
  2162.  
  2163.    # Define a plane that has red and blue checkers
  2164.    object {
  2165.       polynomial y + 0.01
  2166.       texture {
  2167.          checker matte_red, matte_blue
  2168.          }
  2169.       }
  2170.  
  2171. For a sample file, look at "spot0.pi".  This file has a sphere with a red/blue
  2172. checker, and a plane with a black/white checker.
  2173.  
  2174. Note that there is a slight flaw in checkers - at integer boundaries, noise
  2175. can appear.  To clean this up, move the surface just a little bit above or
  2176. below the integer value.  (i.e. in the declaration above and offset of 0.01 was
  2177. used).  Another distinct problem is one of aliasing at great distances.
  2178. To help with aliasing, either use larger checks (by adding a scale to the
  2179. texture), or make sure there is a very low light level at great distances.
  2180.  
  2181. 2.4.3.1.3 Hexagon
  2182.  
  2183. the hexagon texture is oriented in the x-z plane, and has the form:
  2184.  
  2185.    texture {
  2186.       hexagon texture1, texture2, texture3
  2187.       }
  2188.  
  2189. This texture produces a honeycomb tiling of the three textures in the
  2190. declaration.  Remember that this tiling is with respect to the x-z plane, if
  2191. you want it on a vertical wall you will need to rotate the texture.
  2192.  
  2193. 2.4.3.1.4 Noise surfaces
  2194.  
  2195. The complexity and speed of rendering of the noise surface type lies between
  2196. the standard shading model and the special surfaces described below.  It is
  2197. an attempt to capture a large number of the standard 3D texturing operations
  2198. in a single declaration.
  2199.  
  2200. A noise surface declaration has the form:
  2201.  
  2202.      texture {
  2203.         noise surface {
  2204.            [ noise surface definition ]
  2205.            }
  2206.         }
  2207.  
  2208. The allowed surface characteristics that can be defined are:
  2209.  
  2210.    color <r, g, b>          - Basic surface color (used if the noise function
  2211.                               generates a value not contained in the color map)
  2212.    ambient scale            - Amount of ambient contribution
  2213.    diffuse scale            - Diffuse contribution
  2214.    specular color, scale    - Amount and color of specular highlights, if
  2215.                               the color is not given then the body color
  2216.                               will be used.
  2217.    reflection               - Reflectivity of the surface
  2218.    transmission scale, ior  - Amount of refracted light
  2219.    microfacet kind angle    - Specular lighting model (see the 
  2220.                               description of a standard surface)
  2221.  
  2222.    color_map(map_entries)   - Define the color map (see following section on
  2223.                               color map definitions for further details)
  2224.    bump_scale fexper        - How much the bumpiness affects the normal
  2225.    frequency fexper         - Affects the wavelength of ripples and waves
  2226.    phase fexper             - Affects the phase of the ripples and waves
  2227.    lookup_fn index          - Selects a predefined lookup function
  2228.    normal_fn index          - (unused) selects a predefined normal modifier
  2229.    octaves fexper           - Number of octaves of noise to use
  2230.    position_fn index        - How the intersection point is used in the
  2231.                               process of generating a noise texture
  2232.    position_scale fexper    - Amount of contribution of the position value
  2233.                               to the overall texture
  2234.    turbulence fexper        - Amount of contribution of the noise to
  2235.                               overall texture.
  2236.  
  2237. The way the final color of the texture is decided is by calculating a floating
  2238. point value using the following general formula:
  2239.  
  2240.    index = lookup_fn(position_scale * position_fn +
  2241.                      turbulence * noise3d(P, octaves))
  2242.  
  2243. The index value that is calculated is then used to lookup a color from the
  2244. color map.  This final color is used for the ambient, diffuse, reflection and
  2245. transmission filters.  The functions that are currently available, with their
  2246. corresponding indices are:
  2247.  
  2248. Position functions:
  2249.    Index       Effect
  2250.        1        x value in the object coordinate system
  2251.        2        x value in the world coordinate system
  2252.        3        Distance from the z axis
  2253.        4        fractional part of x (in object coordinates)
  2254.        5        fractional part of x * z (in object coordinates)
  2255.        6        distance from the origin (in object coordinates)
  2256.     default:    0.0
  2257.  
  2258. Lookup functions:
  2259.    Index       Effect
  2260.        1        sawtooth function, result from 0 -> 1
  2261.        2        cos function, result from 0->1
  2262.        3        sin function, result from 0->1
  2263.     default:    no modification made
  2264.  
  2265. Definitions of these function numbers that make sense are:
  2266.  
  2267. define position_plain       0
  2268. define position_objectx     1
  2269. define position_worldx      2
  2270. define position_cylindrical 3
  2271. define position_fmodx       4
  2272. define position_fmodxy      5
  2273. define position_fmodxyz     6
  2274.  
  2275. define lookup_plain    0
  2276. define lookup_sawtooth 1
  2277. define lookup_cos      2
  2278. define lookup_sin      3
  2279.  
  2280. An example of a texture defined this way is a simple white marble:
  2281.  
  2282.    define white_marble_texture
  2283.    texture {
  2284.       noise surface {
  2285.          color white
  2286.          position_fn position_objectx
  2287.          lookup_fn lookup_sawtooth
  2288.          octaves 3
  2289.          turbulence 3
  2290.          ambient 0.2
  2291.          diffuse 0.8
  2292.          specular 0.3
  2293.          microfacet Reitz 5
  2294.          color_map(
  2295.             [0.0, 0.8, <1, 1, 1>, <0.6, 0.6, 0.6>]
  2296.             [0.8, 1.0, <0.6, 0.6, 0.6>, <0.1, 0.1, 0.1>])
  2297.          }
  2298.       }
  2299.  
  2300. In addition to coloration, the bumpiness of the surface can be affected
  2301. by selecting a function to modify the normal.  The currently supported
  2302. normal modifier functions are:
  2303.  
  2304.    Index       Effect
  2305.        1        Make random bumps in the surface
  2306.        2        Add ripples to the surface
  2307.        3        Give the surface a dented appearance
  2308.     default:    no change
  2309.  
  2310. See also the file "texture.txt" for a little more explaination.
  2311.  
  2312. 2.4.3.1.5 Radial
  2313.  
  2314. the radial texture is oriented in the x-z plane and has the form:
  2315.  
  2316.    texture {
  2317.       radial radial_count, ratio, width1, width2,
  2318.              texture1, texture2
  2319.       }
  2320.  
  2321. TBD
  2322.  
  2323. Sample files: radial.pi, radial2.pi
  2324.  
  2325. 2.4.3.2 Functional Textures
  2326.  
  2327. The most general, and also the slowest to render are functional textures.
  2328. These textures are evaluated at run-time based on the expressions given for
  2329. the components of the lighting model.  The general syntax for a surface using
  2330. a functional texture is:
  2331.  
  2332.    special surface {
  2333.       [ surface declaration ]
  2334.       }
  2335.  
  2336. In addition to the components usually defined in a surface declaration, it
  2337. is possible to define a function that deflects the normal, and a "body"
  2338. color that will be used as the color filter in the ambient, diffuse, etc.
  2339. components of the surface declaration.  The format of the two declarations
  2340. are:
  2341.  
  2342.    color vexper
  2343. and
  2344.    normal vexper
  2345.  
  2346. An example of how a functional texture can be defined is:
  2347.  
  2348.    define sin_color_offset (sin(3.14 * fmod(x*y*z, 1) + otheta) + 1) / 2
  2349.    define sin_color <sin_color_offset, 0, 1 - sin_color_offset>
  2350.  
  2351.    define xyz_sin_texture
  2352.    texture {
  2353.       special surface {
  2354.          color sin_color
  2355.          ambient 0.2
  2356.          diffuse 0.7
  2357.          specular white, 0.2
  2358.          microfacet Reitz 10
  2359.          }
  2360.       }
  2361.  
  2362. In this example, the color of the surface is defined based on the location
  2363. of the intersection point using the vector defined as "sin_color".  Note that
  2364. sin_color uses yet another definition.
  2365.  
  2366. Sample files: cossph.pi, cwheel.pi.
  2367.  
  2368. 2.4.3.2.1 Image maps
  2369.  
  2370. A type of coloring that can be used involves the use of an existing image
  2371. projected onto a surface.  There are two types of projection supported,
  2372. planar and spherical.  Input files for use as image maps may be 16, 24, and
  2373. 32 bit uncompressed, RLE compressed, or color mapped Targa files.
  2374.  
  2375. The declaration of an image map is:
  2376.  
  2377.    image("imfile.tga")
  2378.  
  2379. Typically, an image will be associated with a variable through a definition
  2380. such as:
  2381.  
  2382.    define myimage image("imfile.tga")
  2383.  
  2384. The image is projected onto a shape by means of a "projection".  The three types
  2385. of projection are declared by:
  2386.  
  2387.    planar_imagemap(image, coordinate [, repeat]),
  2388.    cylindrical_imagemap(image, coordinate [, repeat]),
  2389.    spherical_imagemap(image, coordinate)
  2390.  
  2391. The planar projection maps the entire raster image into the coordinates
  2392. 0 <= x <= 1, 0 <= z <= 1.  The vector value given as "coordinate" is used to
  2393. select a color by multiplying the x value by the number of columns, and the
  2394. z value by the number of rows.  The color appearing at that position in the
  2395. raster will then be returned as the result.  If a "repeat" value is given then
  2396. entire surface, repeating between every integer value of x and/or z.
  2397.  
  2398. The cylindrical projection wraps the image about a cylinder that has one end
  2399. at the origin and the other at <0, 1, 0>.  If a "repeat" value is given, then
  2400. the image will be repeated along the y-axis, if none is given, then any part
  2401. of the object that is not covered by the image will be given the color of pixel
  2402. (0, 0).
  2403.  
  2404. The spherical projection wraps the image about an origin centered sphere.  The
  2405. top and bottom seam are folded into the north and south poles respectively.  The
  2406. left and right edges are brought together on the positive x axis.
  2407.  
  2408. Following are a couple of examples of objects and textures that make use of
  2409. image maps:
  2410.  
  2411.    define hivolt_image image(":dat:hivolt.tga")
  2412.    define hivolt_tex
  2413.    texture {
  2414.       special surface {
  2415.          color cylindrical_imagemap(hivolt_image, P, 1)
  2416.          ambient 0.9
  2417.          diffuse 0.1
  2418.          }
  2419.       scale <1, 2, 1>
  2420.       translate <0, -1, 0>
  2421.       }
  2422.    object { cylinder <0, -1, 0>, <0, 1, 0>, 3 hivolt_tex }
  2423.  
  2424. and
  2425.  
  2426.    define disc_image image("test.tga")
  2427.    define disc_tex
  2428.    texture {
  2429.       special surface {
  2430.          color planar_imagemap(disc_image, P)
  2431.          ambient 0.9
  2432.          diffuse 0.1
  2433.          }
  2434.       translate <-0.5, 0, -0.5>
  2435.       scale <7*4/3, 1, 7>
  2436.       rotate <90, 0, 0>
  2437.       }
  2438.    object {
  2439.       disc <0, 0, 0>, <0, 0, 1>, 6
  2440.       u_steps 10
  2441.       disc_tex
  2442.       }
  2443.  
  2444. 2.5 Comments
  2445.  
  2446. Single line comments are allowed and have the following format:
  2447.  
  2448.     # [ any text to end of the line ]
  2449. or
  2450.    // [ any text to end of the line ]
  2451.  
  2452. As soon as either the "#" character or the two characters "//" are detected,
  2453. the rest of the line is considered a comment.  Future versions of Polyray
  2454. will probably drop support for "#", so don't use it anymore.
  2455.  
  2456. 2.6 Animation support
  2457.  
  2458. An animation is generated by rendering a series of frames, numbered from 0 to
  2459. some total value.  The declarations in polyray that support the generation of
  2460. multiple Targa images are:
  2461.  
  2462.    total_frames val     - The total number of frames in the animation
  2463.    start_frame val      - The value of the first frame to be rendered
  2464.    end_frame val        - The last frame to be rendered
  2465.    outfile "name"
  2466.    outfile name         - Polyray appends the frame number to this string in
  2467.                           order to generate distinct Targa files.
  2468.  
  2469. The values of "total_frames", "start_frame", and "end_frame, as well as the
  2470. value of the current frame, "frame", are usable in arithmetic expressions
  2471. in the input file.  Note that these statements should appear before the use
  2472. of: total_frames, start_frame, end_frame, or frame as a part of an expression.
  2473. Typically I put the declarations right at the top of the file.
  2474.  
  2475. WARNING: if the string given for "outfile" is longer than 5 characters, the
  2476. three digit frame number that is appended will be truncated by DOS.  Make
  2477. sure this string is short enough or you will end up overwriting image files.
  2478.  
  2479. WARNING: a value MUST be specified for "total_frames" in order for animation
  2480. to kick in (even for a single frame).  If no value is given, then the output
  2481. file will not be calculated using "outfile", and only the first frame will
  2482. be generated.
  2483.  
  2484. Sample files: whirl.pi, plane.pi, squish.pi
  2485.  
  2486. 2.7 Conditional processing
  2487.  
  2488. In support of animation geneation (and also because I sometimes like to toggle
  2489. attributes of objects), polyray supports limited conditional processing.  The
  2490. syntax for this is:
  2491.  
  2492.    if (cexper) {
  2493.       [object/light/... declarations]
  2494.       }
  2495.    else {
  2496.       [other object/light/... declarations]
  2497.       }
  2498.  
  2499. The sample file "rsphere.pi" shows how it can be used to modify the color
  2500. characteristics of a moving sphere.
  2501.  
  2502. The use of conditional statements is limited to the top level of the data file.
  2503. You cannot put a conditional within an object or texture declaration. i.e.
  2504.  
  2505.    object {
  2506.       if (foo == 42) {
  2507.          sphere <0, 0, 0>, 4
  2508.          }
  2509.       else {
  2510.          disc <0, 0, 0>, <0, 1, 0>, 4
  2511.          }
  2512.       }
  2513.  
  2514. is not a valid use of an "if" statment, wheras:
  2515.  
  2516.    if (foo == 42) {
  2517.       object {
  2518.          sphere <0, 0, 0>, 4
  2519.          }
  2520.       }
  2521.    else {
  2522.       object {
  2523.          disc <0, 0, 0>, <0, 1, 0>, 4
  2524.          }
  2525.       }
  2526. or
  2527.    if (foo == 42)
  2528.       object { sphere <0, 0, 0>, 4 }
  2529.    else if (foo = 12) {
  2530.       object { torus 3.0, 1.0, <0, 0, 0>, <0, 1, 0> }
  2531.       object { cylinder <0, -1, 0>, <0, 1, 0>, 0.5 }
  2532.       }
  2533.    else
  2534.       object { disc <0, 0, 0>, <0, 1, 0>, 4 }
  2535.  
  2536. are valid.
  2537.  
  2538. Note: the curley brackets "{}" are required if there are multiple statements
  2539. within the conditional, and not required if there is a single staement.
  2540.  
  2541. 2.8 Include files
  2542.  
  2543. In order to allow breaking an input file into several files (as well as
  2544. supporting the use of library files), it is possible to to direct polyray to
  2545. process another file.  The syntax is:
  2546.  
  2547.    include "filename"
  2548.  
  2549. Beware that trying to use "#include ..." will fail as Polyray will consider
  2550. it a comment.
  2551.  
  2552. 2.9 File flush
  2553.  
  2554. Due to unforseen occurances, like power outages, or roommates that hit the
  2555. reset button so they can do word processing, it is possible to specify how
  2556. often the output file will be flushed to disk.  The default is to wait until
  2557. the entire file has been written before a flush (which is a little quicker
  2558. but you lose everything if a crash occurs).
  2559.  
  2560. The format of the declaration is:
  2561.  
  2562.    file_flush xxx
  2563.  
  2564. The number xxx indicates the maximum number of pixels that will be written
  2565. before a file flush will occur.  This value can be as low as 1 - this will
  2566. force a flush after every pixel (only for the very paranoid).
  2567.  
  2568. 3 File formats
  2569.  
  2570. 3.1 Output files
  2571.  
  2572. Currently the output file formats are 16, 24, and 32 bit uncompressed and
  2573. RLE compressed Targa (types 2 and 10).  If no output file is defined with
  2574. the '-o' command line option, the file "out.tga" will be used.  The command
  2575. line option -u specifies that no compression should be used on the output file.
  2576.  
  2577. The default output format is an RLE compressed 16 bit color format.  This
  2578. format holds 5 bits for each of red, green, and blue.  The reason for choosing
  2579. this format is that very few can afford 24 bit color boards and this format
  2580. meets the limits of the typical 8 and 15 bit color boards.  If you have the
  2581. hardware to display more than 32K colors then set the command line switches or
  2582. set the defaults in the initialization file to generate 24 or 32 bit Targa
  2583. files.
  2584.  
  2585. 4 Algorithms
  2586.  
  2587. 4.1 Processing polynomial expressions
  2588.  
  2589. The program in its current form allows the definition of polynomial
  2590. surfaces of degree less than 7 (this value is not fixed, upping it merely
  2591. means a couple of constants need to be changed).
  2592.  
  2593. The way that polynomial expressions are processed and manipulated follows
  2594. the following steps:
  2595.  
  2596.    1) Parse the expression as taken from the input file.  The YACC parser
  2597.       that is used to process the input file creates a parse tree of the
  2598.       expression as it is read.  The format for allowed expressions is
  2599.       described in section 4.1.2.
  2600.       
  2601.    2) Expand the expression into a sum of simple subexpressions.  After
  2602.       the parse tree has been built, the expression is expanded so that
  2603.       the expression is in expanded form. (i.e. (x+1)^2 is rewritten
  2604.       as x^2 + 2*x + 1.)  The rules for doing this are explained in
  2605.       section 4.1.3.
  2606.  
  2607.    3) Determine what order polynomial is represented by the expression.
  2608.       Every term in the expanded expression is examined to see what the
  2609.       largest order of x, y, and z is used.  This determines the order
  2610.       N of the polynomial.  From this value, the number of possible terms
  2611.       of that order is computed.
  2612.  
  2613.    4) Create an array of coefficients for the general three variable
  2614.       polynomial equation of order N.  There are a total of
  2615.       (N+1)*(N+2)*(N+3)/6 terms in the general equation.  The values of
  2616.       each of the coefficients in the expanded expression are then substituted
  2617.       into the array of coefficients.
  2618.  
  2619. Note that the storage of expression is not particularly efficient for high
  2620. orders of N.  This is obviated by the fact that translation and rotation of
  2621. the general polynomial leads to another polynomial of the same order.  In
  2622. this way a set of very simple routines can be used for all polynomial
  2623. equations.  This technique will NOT work well for transcendental expressions,
  2624. and for those the intent is to directly manipulate the parse tree found
  2625. in (1).
  2626.  
  2627. 4.1.1 Example equation representation
  2628.  
  2629. As an example of how the parse tree is expanded, given the input:
  2630.  
  2631.    (x+y)*(1-x-z) + (x-z)^2.
  2632.  
  2633. The expanded representation is:
  2634.  
  2635.    -1*x*y + -3*x*z + x + -1*y*z + y + z^2
  2636.  
  2637. This is a polynomial of order 2, and the array of coefficients is:
  2638.  
  2639.    0 0 1 -1 -3 -1 1 1 0 0
  2640.  
  2641. 4.1.2 Allowed Formula Syntax
  2642.  
  2643. The keyword here is "simple" algebraic expressions.  The only allowed
  2644. variables are "x", "y", and "z" (and only lower case). Constants are floating
  2645. point numbers in the form "n.nnnn" (with or without the decimal point). The
  2646. operations allowed between constants and the three variable symbols
  2647. are: addition, subtraction, multiplication, unary minus, and exponentiation
  2648. by an positive integer power.  Examples of expressions that can be processed are:
  2649.  
  2650.       x^2+y-42
  2651.       (1+x+y+z)^2 * 2*(x-y)*(z-x*(133-z^2))
  2652.       27*x-y*42*y^2
  2653.       (x^2+y^2+z^2+3)^2 - (x*y-x^2)*z^2
  2654.  
  2655. Examples of expressions that cannot be processed are:
  2656.  
  2657.       x/y
  2658.       x^0.5+y
  2659.       2(x-y)
  2660.       x^-2
  2661.  
  2662. 4.1.3 Rules for processing formulas
  2663.  
  2664. There are only a few rules needed to simplify a polynomial expression
  2665. to the point that it can be easily turned into an array of coefficients.
  2666. They appear below, with the letters A, B, C, and D standing for an arbitrary
  2667. sub-expression.  The rules used to simplify an expression are:
  2668.  
  2669.    Addition:
  2670.       No simplification needed for the term: A + B
  2671.  
  2672.    Subtraction:
  2673.       A-B          ->      A + (-B)
  2674.  
  2675.    Unary minus:
  2676.       -(A*B)       ->      (-A * B)
  2677.       -(A+B)       ->      (-A + -B)
  2678.  
  2679.    Multiplication:
  2680.       A*(B+C)      ->      A*B + A*C
  2681.       (A+B)*C      ->      A*C + B*C
  2682.       (A+B)*(C+D)  ->      A*C + A*D + B*C + B*D
  2683.  
  2684.    Exponentiation:
  2685.       (A*B)^n      ->      A^n * B^n
  2686.       (A+B)^n      ->      C(n,0) * A^n + C(n,1) * A^(n-1) * B + ...
  2687.                              C(n,n-1) * A * B^(n-1) + C(n,n) * B^n
  2688.                              { C(n, r) is the binomial coefficient }
  2689.  
  2690. Each of the subexpressions is further simplified until every term in the
  2691. expression has the form: const * x^i * y^j * z^k.
  2692.  
  2693. 4.2 Processing of arbitrary functional surfaces
  2694.  
  2695. The basic algorithm for determining a point of intersection using interval
  2696. math is quite simple:
  2697.  
  2698.    1) Given a range of allowed values for the ray parameter T, a range of
  2699.       function values is calculated.
  2700.  
  2701.    2) If the range does not include 0 then there is no intersection.
  2702.  
  2703.    3) If the range includes 0, then:
  2704.  
  2705.       A) The range of values of the derivative of the function is calculated
  2706.          for the allowed values of the ray parameter T.
  2707.  
  2708.       B) If the range of values of the derivative includes 0, then the
  2709.          interval for T is bisected and we process each subinterval starting
  2710.          with step 1.
  2711.          
  2712.       C) If the range of values of the derivative does not include 0, then
  2713.          we know that there is exactly one solution of the function in the
  2714.          current interval.  A standard root solver using the regula-falsi
  2715.          method is called to find the root.
  2716.  
  2717. There is of course much more to this...
  2718.  
  2719. 4.2.1 Spherical coordinates
  2720.  
  2721. To ray-trace functions that are defined in terms of spherical coordinates
  2722. use the substitutions:
  2723.  
  2724.    r     = sqrt(x^2 + y^2 + z^2),
  2725.    theta = atan(y/x),
  2726.    phi   = atan(sqrt(x^2 + y^2)/z)
  2727.  
  2728. Sample file: zonal.pi
  2729.  
  2730. 4.3 Three dimensional noise generation
  2731.  
  2732. The way Polyray generates noise values from vector inputs follows the following
  2733. steps:
  2734.  
  2735.    1) The integer part of the x, y, and z values of the vector are determined.
  2736.    
  2737.    2) The eight integer points surrounding the input vector are determined.
  2738.    
  2739.    3) A hashing function (described below) is applied to the integer points
  2740.       surrounding the input vector, resulting in eight random numbers.
  2741.       
  2742.    4) A final number is determine by weighting the values associated with the
  2743.       surrounding points with the distance from the input vector to those
  2744.       points.
  2745.  
  2746. The result of this is that each point on an integer lattice has a random value,
  2747. but each fractional value inside a unit cube in the lattice is related to its
  2748. surrounding points.
  2749.  
  2750. The hashing function I use takes the bottom 10 bits of the integer parts of the
  2751. input vector, squishes them into a single number, then crunches this value
  2752. through a series of adds, multiplies, and mods to get a single result.  The
  2753. algorithm is:
  2754.  
  2755.    K = ((x & 0x03ff) << 20) |
  2756.        ((y & 0x03ff) << 10) |
  2757.         (z & 0x03ff);
  2758.    Kt = 0;
  2759.    for (i=0;i<mult_table_size;i++)
  2760.       Kt = ((Kt + K) * mult_table[i]) % HASH_SIZE;
  2761.    result = (Flt)Kt / (Flt)(HASH_SIZE - 1);
  2762.  
  2763. The number and value of the entries in "mult_table" were chosen at random, as
  2764. was the value HASH_SIZE.  I haven't bothered to determine if the results from
  2765. this hashing function really are spread evenly, however the visual results
  2766. from using it are quite good.
  2767.  
  2768. 4.4 Marching Cubes
  2769.  
  2770. The marching cubes algorithm puts a lattice over the three dimensional space
  2771. that an object sits in.  By stepping through each subcube in the lattice and
  2772. looking for places where the surface passes through a subcube, a good guess
  2773. at a polygonal cover for the surface can be generated.  This algorithm is
  2774. used for scan converting blobs, polynomial functions, and implicit functions.
  2775.  
  2776. As each cube is processed, every vertex of the cube is tested to see if it
  2777. is inside the object "hot", or outside the object "cold".  There are a total
  2778. of 2^8 = 256 possible combinations of hot and cold vertices.
  2779.  
  2780. The processing of each subcube in the lattice takes these steps:
  2781.  
  2782.    o Each of the 8 vertices of the cube corresponds to a bit in an
  2783.      unsigned char.  If the vertex is hot then the bit is set to 1, if
  2784.      the vertex is cold the bit is set to 0.
  2785.  
  2786.    o Using a little combinatorics and group theory, it is possible to to
  2787.      classify, under the group of solid rotations of the cube, each of the
  2788.      256 possibilities to one of 23 unique base cases.
  2789.  
  2790.    o Each of the base cases has an entry in a table of triangles that
  2791.      separate the hot vertices from the cold vertices for that case.
  2792.  
  2793.    o By using the inverse of the rotations that took the cube into the
  2794.      base case, the triangles are rotated to separate the hot and cold
  2795.      vertices of the original cube.
  2796.  
  2797.    o The amount of hot and amount of cold that are separated by each
  2798.      triangle is examined in order to see how much to push the triangle
  2799.      up or down.  This is a linear interpolation that helps to keep the
  2800.      triangles close to the actual surface.
  2801.  
  2802.    o Now that the triangles are known and in approximately the right place,
  2803.      the normal scan conversion routine is called for each triangle.
  2804.  
  2805. The biggest drawback of this algorithm is that the number of evaluations
  2806. goes up with the cube of the resolution of the lattice.  For example,
  2807. if u_steps is 20 and v_steps is 20 (the default), then 20x20x20 = 8000
  2808. individual subcubes are visited.  If you were to increase the resolution
  2809. by a factor of 5, there would be 100x100x100 = 1,000,000 subcubes visited.
  2810.  
  2811. Another problem is one of aliasing.  If the surface is very complex and/or
  2812. contains many small features, and the number of steps along the axes is
  2813. insufficient to properly determine inside/outside, then large portions of
  2814. the surface can disappear.  The solution is to increase the step sizes,
  2815. or to raytrace, either option will increase processing time.
  2816.  
  2817. Note: when I built the table of triangles, I made the assumption that if
  2818. there are two ways to split hot from cold, that hot would always connect
  2819. to hot.  One example of this choice is when the the vertices: (0, 0, 0),
  2820. (1, 0, 0), (0, 1, 1), and (1, 1, 1) are all hot and the rest are cold.
  2821.  
  2822. 5 Outstanding Issues
  2823.  
  2824. Polyray will probably never be "done".  And in this respect, the next two
  2825. sections list some things that are planned for the future, as well as things
  2826. that should already have been fixed.
  2827.  
  2828. 5.1 To do list
  2829.  
  2830.    Parameterised objects and textures.  This will occur in the next major
  2831.    release of Polyray, due to the extreme structural changes required.
  2832.  
  2833.    Support for the black and white Targa image formats, in particular:
  2834.        Type  3  -  Uncompressed, black and white images.
  2835.        Type 11  -  Compressed, black and white images.
  2836.  
  2837.    Simplified support for "see-through" textures.  This facility exists
  2838.    in the POV-Ray raytracer as layered textures.  Polyray will support
  2839.    this type of texturing in the form of texture maps having a similar
  2840.    format as the current color maps.
  2841.    
  2842.    The ability to execute a "system" command.  During the generation of an
  2843.    animation it would be nice to call an external program that in turn generates
  2844.    an include file containing data for the current frame of the animation.
  2845.  
  2846.    User definable positioning of display elements, in particular placement of
  2847.    the image as it is drawn, and placement of the status display during the
  2848.    trace.
  2849.  
  2850.    Appending ".pi" to input file names that do not have an extension.
  2851.  
  2852. 5.2 Known Bugs
  2853.  
  2854.    Bounding slabs sometimes screw up shadows
  2855.  
  2856.    It is possible to specify surface components that have no meaning for
  2857.    the type of surface that is being declared. i.e. octaves in a special
  2858.    surface.
  2859.  
  2860.    Polyray still seems to eat a little memory between frames of an animation.
  2861.    The amount has been reduced from previous versions, and may simply be a
  2862.    function of fragmentation.
  2863.  
  2864.    The initialization file "polyray.ini" has to be in the current directory.
  2865.  
  2866.    Shading in scan conversion doesn't always match that from raytracing.
  2867.  
  2868.    Refraction does not appear to be correct when the ray passes through
  2869.    several overlapping transparent objects. Works fine if the ior is 1.0, or
  2870.    if there is only 1 object intersected by the ray.
  2871.  
  2872.    Height fields sometimes have small holes in them.
  2873.  
  2874. 6 Revision History
  2875.  
  2876. Version 1.4
  2877. Released: 11 April 1992
  2878.  
  2879. This will be the last DOS hosted version of Polyray.  All future releases
  2880. will require Windows.
  2881.  
  2882.    Support for many SVGA boards at 640x480 resolution in 256 colors.  See
  2883.    documentation for the -V flag. (Note: SVGA displays only work on the
  2884.    286 versions.)
  2885.  
  2886.    Changed the way the status output is managed.  Now requires a number
  2887.    following the -t flag.  Note that line and pixel status will screw
  2888.    up SVGA displays - drawing goes to the wrong place starting around
  2889.    line 100.  If using SVGA display then either use no status, or "totals".
  2890.  
  2891.    Added cylindrical blob components.  Changed the syntax for blobs to
  2892.    accomodate the new type.
  2893.  
  2894.    Added lathe surfaces made from either line segments or quadratic
  2895.    splines.
  2896.  
  2897.    Added sweep surfaces made from quadratic splines.
  2898.  
  2899.    Height field syntax changed slightly.  Non-square height fields now
  2900.    handled correctly.
  2901.  
  2902.    Added adaptive antialiasing.
  2903.  
  2904.    Squashed bug in shading routines that affected almost all primitives.
  2905.    This bug was most noticible for objects that were scaled using different
  2906.    values for x, y, and z.
  2907.  
  2908.    Added transparency values to color maps.
  2909.  
  2910.    Added new keywords to the file "polyray.ini": shadow_tolerance, antialias,
  2911.    alias_threshold, max_samples.  Lines that begin with "// " in polyray.ini
  2912.    are now treated as comments.
  2913.    
  2914.    Short document called "texture.txt" is now included in "plydoc.zip".  This
  2915.    describes in a little more detail how to go about developing solid textures
  2916.    using Polyray.
  2917.  
  2918.    Added command line argument "-z start_line".  This allows the user to start
  2919.    a trace somewhere in the middle of an image.  Note that an image that was
  2920.    started this way cannot be correctly resumed & completed.  (You may be able
  2921.    to paste utilities though.)
  2922.  
  2923. Version 1.3
  2924. (not released)
  2925.  
  2926.    Added support for scan converting implicit functions and polynomial
  2927.    surfaces using the marching cubes algorithm.  This technique can be
  2928.    slow, and is restricted to objects that have user defined bounding shapes,
  2929.    but now Polyray is able to scan convert any primitive.
  2930.  
  2931.    A global shading flag has been added in order to selectively turn on/off
  2932.    some of the more time consuming shading options.  This option will also
  2933.    allow for the use of raytracing as a way of determining shadows,
  2934.    reflectivity, and transparency during scan conversion.
  2935.  
  2936.    Added new keywords to the file "polyray.ini": pixel_size, pixel_encoding,
  2937.    shade_flags.
  2938.  
  2939.    Improved refraction code to (mostly) handle transparent surfaces that
  2940.    are defined by CSG intersection.
  2941.  
  2942.    Fixed miscoloring of shadows that receive some light through a transparent
  2943.    object.
  2944.  
  2945.    Jittered antialiasing was not being called when the option was selected,
  2946.    this has been fixed.
  2947.  
  2948.    Fixed parsing of blobs and polygons that had large numbers of entries.
  2949.    Previously the parser would fail after 50-60 elements in a blob and the
  2950.    same number of vertices of a polygon.
  2951.  
  2952.    In keeping with the format used by POV-Ray and Vivid, comments may now
  2953.    start with "//" as well as "#".  The use of the pound symbol for comments
  2954.    may be phased out in future versions.
  2955.  
  2956. Version 1.2
  2957. Released: 16 February 1992
  2958.  
  2959.    Scan conversion of many primitives, using Z-Buffer techniques.
  2960.  
  2961.    New primitives: sweep surface, torus
  2962.  
  2963.    Support for the standard 320x200 VGA display in 256 colors.
  2964.  
  2965.    An initialization file ("polyray.ini") is read before processing.  This
  2966.    allows greater flexibility in tuning many of the default values used by
  2967.    Polyray.
  2968.  
  2969.    User defined bounding slabs added.  This greatly improves speed of rendering
  2970.    on data files with many small objects.
  2971.  
  2972.    Noise surface added.
  2973.  
  2974.    Symbol table routines completely reworked.  Improved speed for data files
  2975.    containing many definitions.
  2976.  
  2977.    Bug in the texturing of height fields corrected.
  2978.  
  2979. Version 1.1
  2980. (not released)
  2981.  
  2982.    Added parabola primitive
  2983.    
  2984.    Dithering of rays, and objects
  2985.    
  2986.    Blob code improved, shading corrected, intersection code is
  2987.    faster and returns fewer incorrect results.
  2988.  
  2989. Version 1.0
  2990. Released: 27 December 1991
  2991.  
  2992.    Several changes in input syntax were made, the most notable result being
  2993.    that commas are required in many more places.  The reason for this is that
  2994.    due to the very flexible nature of expressions possible, a certain amount of
  2995.    syntatic sugar is required to remove ambiguities from the parser.
  2996.  
  2997.    Several new primitives were added: boxes, cones, cylinders, discs, height
  2998.    fields, and Bezier patches.
  2999.  
  3000.    A new way of doing textures was added - each component of the lighting
  3001.    model can be specified by an implicit function that is evaluated at run
  3002.    time.  Using this feature leads to slower textures, however because the
  3003.    textures are defined in the data file instead of within Polyray, development
  3004.    of mathematical texturing can be developed without making alterations to
  3005.    Polyray.
  3006.  
  3007.    File flush commands in the data file and at the command line were added.
  3008.  
  3009.    Several new Targa variants were added.
  3010.  
  3011.    Image mapping added.
  3012.  
  3013.    Numerous bug fixes have occured.
  3014.  
  3015. Version 0.3 (beta)
  3016. Released: 14 October 1991
  3017.  
  3018.    This release added Constructive Solid Geometry, functional surfaces defined
  3019.    in terms of transcendental functions, a checker texture, and compressed
  3020.    Targa output.
  3021.  
  3022.    Polyray no longer accepted a list of bounding/clipping objects, only
  3023.    a single object is allowed. since CSG can be used to define complex shapes, 
  3024.    this is not a limitation, and even better makes for cleaner data files.
  3025.  
  3026. Version 0.2 (beta)
  3027. (not released)
  3028.  
  3029.    This release added animation support, defined objects, arithemetic expression
  3030.    parsing, and blobs.
  3031.  
  3032. Version 0.1 (beta)
  3033. (not released)
  3034.  
  3035.    First incarnation of Polyray.  This version had code for polynomial equations
  3036.    and some of the basic surface types contained in "mtv".
  3037.  
  3038. 7 Bibliography
  3039.  
  3040.       "Introduction to Ray Tracing"
  3041.       Edited by Andrew Glassner
  3042.       Academic Press, 1989
  3043.  
  3044.       "Illumination and Color in Computer Generated Imagery"
  3045.       Roy Hall
  3046.       Springer Verlag, 1989
  3047.  
  3048.       "Numerical Recipes in C"
  3049.       Press, et al.
  3050.       Cambridge University Press, 1988
  3051.  
  3052.       "CRC Handbook of Mathematical Curves and Surfaces"
  3053.       David H. von Seggern
  3054.       CRC Press, 1990
  3055.  
  3056.       "Robust Ray Intersection with Interval Arithematic"
  3057.       D.P. Mitchell,
  3058.       from:
  3059.          "Proceedings Graphics Interface '90"
  3060.          Canadian Information Processing Society
  3061.  
  3062. 8 Sample files
  3063.  
  3064. 8.1 Full sample
  3065.  
  3066. The following listing (taken from "torus.pi") defines a torus as well as
  3067. a spherical bound around the torus (spheres are much quicker to test for).
  3068. The major radius of the torus is 0.5, the minor radius is 0.2.  In the
  3069. equation defining the shape of the torus, these numbers appear exactly twice.
  3070. Note that the Torus primitive could have been used instead of a quartic.
  3071.  
  3072.    // Set up the camera
  3073.    viewpoint {
  3074.       from <0, 5, -5>
  3075.       at   <0, 0,  0>
  3076.       up   <0, 1,  0>
  3077.       angle 30
  3078.       resolution 160, 160
  3079.       }
  3080.  
  3081.    // Get various surface finishes
  3082.    include "colors.inc"
  3083.  
  3084.    // Set up background color & lights
  3085.    background black
  3086.    light <10, 10, -20>
  3087.  
  3088.    // Torus - basic doughnut shape.  The distance from the origin to the center
  3089.    // of the ring is "r0", the distance from the center of the ring to the
  3090.    // surface is "r1".  The hole of the doughnut is lined up with the z-axis.
  3091.    define r0 1
  3092.    define r1 0.4
  3093.  
  3094.    // Define the equation of a torus, using the radii above
  3095.    define torus_expression (x^2 + y^2 + z^2 - (r0^2 + r1^2))^2 -
  3096.                            4 * r0^2 * (r1^2 - z^2)
  3097.    object {
  3098.       polynomial torus_expression
  3099.       root_solver Ferrari
  3100.       shiny_red
  3101.       bounds object { box <-(r0+r1), -(r0+r1), -r1>,
  3102.                           < (r0+r1),  (r0+r1),  r1> }
  3103.       rotate <20,0,0>
  3104.       translate <0,0,2>
  3105.       }
  3106.  
  3107. By changing the values of r0, and r1, the shape of the torus can be affected.
  3108.  
  3109. 8.2 List of Sample Files
  3110.  
  3111. A number of sample files are referenced in this document.  These files
  3112. are contained in a separate archive, and demonstrate various features
  3113. of Polyray.
  3114.  
  3115. Simple demo files:
  3116.  
  3117.      boxes.pi           cone.pi      cossph.pi     cwheel.pi
  3118.   cylinder.pi           disc.pi     gsphere.pi     sphere.pi
  3119.      spot0.pi
  3120.  
  3121. Sample color/texture definitions:
  3122.  
  3123.     colors.inc
  3124.  
  3125. Polynomial surfaces:
  3126.  
  3127.     bicorn.pi        bifolia.pi     cassini.pi      csaddle.pi
  3128.      devil.pi         folium.pi       helix.pi     hyptorus.pi
  3129.    kampyle.pi       lemnisca.pi        loop.pi       monkey.pi
  3130.    parabol.pi       partorus.pi    piriform.pi       qparab.pi
  3131.    qsaddle.pi        quarcyl.pi    quarpara.pi      steiner.pi
  3132.   strophid.pi         tcubic.pi       tear5.pi        torus.pi
  3133.     trough.pi       twincone.pi    twinglob.pi        witch.pi
  3134.  
  3135. Implicit function surfaces
  3136.  
  3137.    sectorl.pi       sombrero.pi     sinsurf.pi       superq.pi
  3138.      zonal.pi
  3139.  
  3140. Bezier patches
  3141.  
  3142.    bezier0.pi         teapot.pi      teapot.inc
  3143.  
  3144. Height Fields
  3145.  
  3146.     hfnoise.pi        sombfn.pi       sinfn.pi        wake.pi
  3147.  
  3148. Image mapping
  3149.  
  3150.       map1.pi
  3151.  
  3152. Texturing, CSG, etc.
  3153.  
  3154.       lens.pi       lookpond.pi      marble.pi     polytope.pi
  3155.      spot1.pi           wood.pi      xander.pi
  3156.       
  3157. Data file generators:
  3158.  
  3159.      balls.c            coil.c        gears.c       hilbert.c
  3160.   mountain.c         sphcoil.c        tetra.c
  3161.  
  3162. Animation files:
  3163.  
  3164.       plane.pi        squish.pi       whirl.pi
  3165.       
  3166. 9 Polyray Grammar
  3167.  
  3168. What follows is the complete YACC grammar used to parse Polyray input files.
  3169. Only the actions taken at each rule have been deleted.  The conventions used
  3170. in the grammar are: keywords (terminal symbols like "sphere") appear in all
  3171. caps, i.e. SPHERE.  All other grammar rules (nonterminals) appear in lower
  3172. case.  The terminal symbols, including punctuation, are either recognized by
  3173. the lexical analyzer or by lookup from one of the symbol tables.  (Note there
  3174. is one ambiguity present in the grammar - the "if .. if .. else" construct.)
  3175.  
  3176. scene
  3177.    : elementlist 
  3178.    ;
  3179.  
  3180. elementlist
  3181.    : elementlist element
  3182.    | element
  3183.    ;
  3184.  
  3185. element
  3186.    : background
  3187.    | camera
  3188.    | definition
  3189.    | flush_statement
  3190.    | frame_decl
  3191.    | if_statement
  3192.    | include_statement
  3193.    | light
  3194.    | object
  3195.    | outfile
  3196.    | slab_declaration
  3197.    ;
  3198.  
  3199. token
  3200.    : SURFACE_SYM
  3201.    | TEXTURE_SYM
  3202.    | OBJECT_SYM
  3203.    | STRING_SYM
  3204.    | EXPRESSION_SYM
  3205.    | TOKEN
  3206.    ;
  3207.  
  3208. definition
  3209.    : DEFINE token STRING_SYM
  3210.    | DEFINE token surface
  3211.    | DEFINE token texture
  3212.    | DEFINE token object
  3213.    | DEFINE token expression
  3214.    ;
  3215.  
  3216. object
  3217.    : OBJECT '{' object_decls '}'
  3218.    | OBJECT_SYM
  3219.    | OBJECT_SYM '{' object_modifier_decls '}'
  3220.    ;
  3221.  
  3222. object_modifier_decls
  3223.    : object_modifier_decl object_modifier_decls
  3224.    | object_modifier_decl
  3225.    ;
  3226.  
  3227. object_modifier_decl
  3228.    : texture
  3229.    | DITHER fexper
  3230.    | ROTATE point
  3231.    | SHEAR fexper ',' fexper ',' fexper ',' fexper ','
  3232.            fexper ',' fexper
  3233.    | TRANSLATE point
  3234.    | SCALE point
  3235.    | U_STEPS fexper
  3236.    | V_STEPS fexper
  3237.    | SHADING_FLAGS fexper
  3238.    | BOUNDS object
  3239.    | CLIPS object
  3240.    | ROOT_SOLVER FERRARI
  3241.    | ROOT_SOLVER VIETA
  3242.    | ROOT_SOLVER STURM
  3243.    ;
  3244.  
  3245. object_decls
  3246.    : shape_decl
  3247.    | shape_decl object_modifier_decls
  3248.    ;
  3249.  
  3250. shape_decl
  3251.    : bezier
  3252.    | blob
  3253.    | box
  3254.    | cone
  3255.    | cylinder
  3256.    | csg
  3257.    | disc
  3258.    | function
  3259.    | height_field
  3260.    | height_fn
  3261.    | lathe
  3262.    | parabola
  3263.    | polygon
  3264.    | polynomial
  3265.    | ppatch
  3266.    | sphere
  3267.    | sweep
  3268.    | torus
  3269.    ;
  3270.  
  3271. camera_exper
  3272.    : ANGLE fexper
  3273.    | AT point
  3274.    | ASPECT fexper
  3275.    | MAX_TRACE_DEPTH fexper
  3276.    | DITHER_RAYS fexper
  3277.    | DITHER_OBJECTS fexper
  3278.    | FROM point
  3279.    | HITHER fexper
  3280.    | YON fexper
  3281.    | RESOLUTION fexper ',' fexper
  3282.    | UP point
  3283.    ;
  3284.  
  3285. camera_expers
  3286.    : camera_expers camera_exper
  3287.    | camera_exper
  3288.    ;
  3289.  
  3290. camera
  3291.    : VIEWPOINT '{' camera_expers '}'
  3292.    ;
  3293.  
  3294. light
  3295.    : LIGHT point ',' point 
  3296.    | LIGHT point 
  3297.    | SPOT_LIGHT point ',' point
  3298.    | SPOT_LIGHT point ',' point ',' point ',' fexper ',' fexper ',' fexper
  3299.    ;
  3300.  
  3301. background
  3302.    : BACKGROUND expression
  3303.    ;
  3304.  
  3305. slab_declaration
  3306.    : BOUNDING_SLAB point
  3307.    ;
  3308.  
  3309. surface_declaration
  3310.    : COLOR expression
  3311.    | COLOR_MAP '(' map_entries ',' expression ')'
  3312.    | COLOR_MAP '(' map_entries ')'
  3313.    | AMBIENT expression ',' expression
  3314.    | AMBIENT expression
  3315.    | BUMP_SCALE expression
  3316.    | DIFFUSE expression ',' expression
  3317.    | DIFFUSE expression
  3318.    | FREQUENCY expression
  3319.    | LOOKUP_FUNCTION expression
  3320.    | MICROFACET PHONG expression
  3321.    | MICROFACET BLINN expression
  3322.    | MICROFACET GAUSSIAN expression
  3323.    | MICROFACET REITZ expression
  3324.    | MICROFACET COOK expression
  3325.    | MICROFACET expression
  3326.    | NORMAL expression
  3327.    | OCTAVES expression
  3328.    | PHASE expression
  3329.    | POSITION_FUNCTION expression
  3330.    | POSITION_SCALE expression
  3331.    | REFLECTION expression ',' expression
  3332.    | REFLECTION expression
  3333.    | SPECULAR expression ',' expression
  3334.    | SPECULAR expression
  3335.    | TRANSMISSION expression ',' expression ',' expression
  3336.    | TRANSMISSION expression ',' expression
  3337.    | TURBULENCE expression
  3338.    ;
  3339.  
  3340. surface_declarations
  3341.    : surface_declaration surface_declarations
  3342.    |
  3343.    ;
  3344.  
  3345. surface
  3346.    : SURFACE '{' surface_declarations '}'
  3347.    | SURFACE_SYM
  3348.    | SURFACE_SYM '{' surface_declarations '}'
  3349.    ;
  3350.  
  3351. texture_modifier_decls
  3352.    : texture_modifier_decl texture_modifier_decls
  3353.    | texture_modifier_decl
  3354.    ;
  3355.  
  3356. texture_modifier_decl
  3357.    : ROTATE point
  3358.    | SHEAR fexper ',' fexper ',' fexper ',' fexper ','
  3359.            fexper ',' fexper
  3360.    | TRANSLATE point
  3361.    | SCALE point
  3362.    ;
  3363.  
  3364. texture_declarations
  3365.    : texture_declaration texture_modifier_decls
  3366.    | texture_declaration
  3367.    ;
  3368.  
  3369. texture_declaration
  3370.    : surface
  3371.    | SPECIAL surface
  3372.    | NOISE surface
  3373.    | CHECKER texture ',' texture
  3374.    | HEXAGON texture ',' texture ',' texture
  3375.    | RADIAL fexper ',' fexper ',' fexper ',' fexper ',' texture ',' texture
  3376.    ;
  3377.  
  3378. texture
  3379.    : TEXTURE '{' texture_declarations '}'
  3380.    | TEXTURE_SYM
  3381.    | TEXTURE_SYM '{' texture_modifier_decls '}'
  3382.    ;
  3383.  
  3384. bezier_points
  3385.    : bezier_points ',' point
  3386.    | point
  3387.    ;
  3388.  
  3389. bezier
  3390.    : BEZIER fexper ',' fexper ',' fexper ',' fexper ',' bezier_points
  3391.    ;
  3392.  
  3393. blob
  3394.    : BLOB fexper ':' blobelements
  3395.    ;
  3396.  
  3397. blobelements
  3398.    : blobelement
  3399.    | blobelements ',' blobelement
  3400.    ;
  3401.  
  3402. blobelement
  3403.    : fexper ',' fexper ',' point
  3404.    | SPHERE point ',' fexper ',' fexper
  3405.    | CYLINDER point ',' point ',' fexper ',' fexper
  3406.    ;
  3407.  
  3408. box
  3409.    : BOX point ',' point 
  3410.    ;
  3411.  
  3412. cone
  3413.    : CONE point ',' fexper ',' point ',' fexper
  3414.    ;
  3415.  
  3416. csg
  3417.    : csg_tree
  3418.    ;
  3419.  
  3420. csg_tree
  3421.    : '(' csg_tree ')'
  3422.    | csg_tree '+' csg_tree
  3423.    | csg_tree '-' csg_tree
  3424.    | csg_tree '*' csg_tree
  3425.    | '~' csg_tree
  3426.    | object
  3427.    ;
  3428.  
  3429. cylinder
  3430.    : CYLINDER point ',' point ',' fexper
  3431.    ;
  3432.  
  3433. disc
  3434.    : DISC point ',' point ',' fexper
  3435.    | DISC point ',' point ',' fexper ',' fexper
  3436.    ;
  3437.  
  3438. function
  3439.    : FUNCTION expression
  3440.    ;
  3441.  
  3442. height_field
  3443.    : HEIGHT_FIELD STRING_SYM
  3444.    ;
  3445.  
  3446. height_fn
  3447.    : HEIGHT_FN fexper ',' fexper ','
  3448.                fexper ',' fexper ',' fexper ',' fexper ','
  3449.                expression
  3450.    | HEIGHT_FN fexper ',' fexper ',' expression
  3451.    ;
  3452.  
  3453. lathe
  3454.    : LATHE fexper ',' point ',' fexper  ',' pointlist 
  3455.    ;
  3456.  
  3457. parabola
  3458.    : PARABOLA point ',' point ',' fexper
  3459.    ;
  3460.  
  3461. polygon:
  3462.    POLYGON fexper  ',' pointlist 
  3463.    ;
  3464.  
  3465. polynomial
  3466.    : POLYNOMIAL expression
  3467.    ;
  3468.  
  3469. ppatch
  3470.    : PATCH point ',' point ',' point ',' point ',' point ',' point
  3471.    ;
  3472.  
  3473. sphere
  3474.    : SPHERE point ',' fexper 
  3475.    ;
  3476.  
  3477. sweep
  3478.    : SWEEP fexper ',' point ',' fexper  ',' pointlist 
  3479.    ;
  3480.  
  3481. torus
  3482.    : TORUS fexper ',' fexper ',' point ',' point 
  3483.    ;
  3484.  
  3485. point
  3486.    : expression
  3487.    ;
  3488.  
  3489. fexper
  3490.    : expression
  3491.    ;
  3492.  
  3493. pointlist
  3494.    : point
  3495.    | pointlist ',' point
  3496.    ;
  3497.  
  3498. expression
  3499.    : '(' expression ')'
  3500.    | '<' expression ',' expression '>'
  3501.    | '<' expression ',' expression ',' expression '>'
  3502.    | expression '[' expression ']'
  3503.    | '(' conditional '?' expression ':' expression ')'
  3504.    | expression '^' expression
  3505.    | expression '*' expression
  3506.    | expression '.' expression
  3507.    | expression '/' expression
  3508.    | expression '+' expression
  3509.    | expression '-' expression
  3510.    | '-' expression %prec UMINUS
  3511.    | '|' expression '|'
  3512.    | COLOR_MAP '(' map_entries ',' expression ')'
  3513.    | COLOR_MAP '(' map_entries ')'
  3514.    | NOISE '(' expression ')'
  3515.    | NOISE '(' expression ',' expression ')'
  3516.    | IMAGE '(' STRING_SYM ')'
  3517.    | ROTATE '(' expression ',' expression ')'
  3518.    | END_FRAME
  3519.    | START_FRAME
  3520.    | TOTAL_FRAMES
  3521.    | TOKEN '(' expression_list ')'
  3522.    | TOKEN
  3523.    | NUM
  3524.    | EXPRESSION_SYM
  3525.    ;
  3526.  
  3527. expression_list
  3528.    : expression
  3529.    | expression ',' expression_list
  3530.    ;
  3531.  
  3532. conditional
  3533.    : expression '<' expression
  3534.    | expression '>' expression
  3535.    | expression LTEQ_SYM expression
  3536.    | expression GTEQ_SYM expression
  3537.    | expression EQUAL_SYM expression
  3538.    | expression AND_SYM expression
  3539.    | expression OR_SYM expression
  3540.    | '!' conditional
  3541.    ;
  3542.  
  3543. map_entry
  3544.    : '[' fexper ',' fexper ',' point ',' point ']'
  3545.    | '[' fexper ',' fexper ',' point ',' fexper ',' point ',' fexper ']'
  3546.    ;
  3547.  
  3548. map_entries
  3549.    : map_entry map_entries
  3550.    | map_entry
  3551.    ;
  3552.  
  3553. frame_decl
  3554.    : end_frame_decl
  3555.    | start_frame_decl
  3556.    | total_frames_decl
  3557.    ; 
  3558.  
  3559. end_frame_decl
  3560.    : END_FRAME fexper
  3561.    ;
  3562.  
  3563. start_frame_decl
  3564.    : START_FRAME fexper
  3565.    ;
  3566.  
  3567. total_frames_decl
  3568.    : TOTAL_FRAMES fexper
  3569.    ;
  3570.  
  3571. outfile
  3572.    : OUTFILE TOKEN
  3573.    | OUTFILE STRING_SYM
  3574.    ;
  3575.  
  3576. include_statement
  3577.    : INCLUDE STRING_SYM
  3578.    ;
  3579.  
  3580. flush_statement
  3581.    : FILE_FLUSH fexper
  3582.    ;
  3583.  
  3584. statement
  3585.    : '{' elementlist '}'
  3586.    | element
  3587.    ;
  3588.  
  3589. if_else_part
  3590.    : ELSE statement
  3591.    |
  3592.    ;
  3593.  
  3594. if_statement
  3595.    : IF '(' conditional ')' statement if_else_part
  3596.    ;
  3597.  
  3598.  
  3599.  
  3600.